07 矩阵路径求和

题目描述

构造一个 $n \times m$ 的矩阵($n \times m \leq 200$),每个单元格填入非负整数。对于 $q$ 次询问,每次给出一个非负整数 $S$,需要找到一条从 $(1,1)$ 到 $(n,m)$ 的路径,满足:

  1. 每个单元格至多被经过一次
  2. 路径上所有数字之和等于 $S$

思路分析

如何思考这个问题?

当我们第一次看到这个问题时,可能会尝试各种复杂的图论算法。但仔细分析会发现几个关键点:

  1. 数字范围很大:$S \leq 10^{18}$,但矩阵大小有限制($\leq 200$)
  2. 每个单元格只能经过一次:这意味着路径是唯一的,不能走回头路

二进制的启发

想到二进制表示是自然的:

  • 任何整数 $S$ 都可以表示为 $2^{a_1} + 2^{a_2} + \cdots + 2^{a_k}$
  • 如果我们能让路径”选择性地”经过某些单元格,每个单元格的值是 $2^i$,那么只要控制哪些 $2^i$ 被经过,就能拼出任意 $S$

这就是核心洞察:把 $S$ 拆成二进制位,路径经过第 $i$ 行代表取 $2^i$

构造的难点与解决

但直接这样构造会遇到问题:如果每次都走同样的列,路径会重复经过同一个单元格。

解决方法是利用奇偶性

  • flag 标志位交替使用 RR(向右向右)和 LL(向左向左)
  • 这样虽然目的都是向右移动到中间列,但走的路径不同,避免重复

最终方案

  • 矩阵用 $(n+1) \times 3$ 的形状,其中 $n = \lceil \log2(S{max}) \rceil$
  • 每行中间放置 $2^i$,其余为 0
  • 路径根据二进制位决定是否”绕路”取这个值

解题思路

核心思想:二进制表示

对于任意 $S \leq 10^{18}$,我们可以用二进制表示。关键发现是:

  • $S$ 的二进制表示中第 $i$ 位为 1 时,我们需要在路径中添加 $2^i$
  • $S$ 的二进制表示中第 $i$ 位为 0 时,我们不需要添加 $2^i$

矩阵构造

构造一个 $(n+1) \times 3$ 的矩阵,其中 $n$ 是最大查询值 $S_{max}$ 的二进制位数:

i 行 (0i < n): 0  2^i  0
第 n 行:             0  0   0

例如当 $n=3$ 时(对应 $S_{max}=7$):

0 1 0
0 2 0
0 4 0
0 0 0

路径构造

从 $(1,1)$ 出发,对于 $S$ 的二进制每一位:

  • 若第 $i$ 位为 1:先向右走到中间列(取到 $2^i$),再向下走
  • 若第 $i$ 位为 0:直接向下走

最后根据标志位决定是否需要额外的向右移动到达终点。

代码实现

import sys
input = sys.stdin.readline

q = int(input())
S_list = [int(input()) for _ in range(q)]
n = max(S_list).bit_length()  # 最大S的二进制位数

print(n + 1, 3)
for i in range(n):
    print(0, 1 << i, 0)
print("0 0 0")

for S in S_list:
    path = []
    flag = 1  # 奇偶标志,决定RR还是LL
    for i in range(n):
        if (S >> i) & 1:
            path.extend(['RR' if flag else 'LL', 'D'])
            flag ^= 1
        else:
            path.append('D')
    if flag:
        path.append('RR')
    print(''.join(path))

复杂度分析

  • 矩阵大小:$(n+1) \times 3 \leq 61 \times 3 = 183 \leq 200$ ✓
  • 时间复杂度:$O(q \cdot n)$,其中 $n = \log2(S{max}) \leq 60$
  • 空间复杂度:$O(1)$

代码说明

  1. n = max(S_list).bit_length() 计算最大查询值的二进制位数
  2. 矩阵构造:前 $n$ 行中间列为 $2^0, 2^1, \ldots, 2^{n-1}$,最后一行全为 0
  3. 路径构造使用标志位 flag 交替使用 RRLL,确保路径不重复经过单元格

07 矩阵路径求和
https://mingsm17518.github.io/2026/03/18/algorithm/solutions/2025_SDU_Star_Remake/07-matrix-path-sum/
作者
Ming
发布于
2026年3月18日
更新于
2026年3月19日
许可协议