📅  最后修改于: 2023-12-03 15:25:36.519000             🧑  作者: Mango
在2D矩阵中找到最大路径总和是一个经典的动态规划问题。给定一个矩阵,每个格子里有一个值,你需要找到一条从左上角到右下角的路径,使得沿路径走过的值得总和最大。
需要注意的是,题目中给定的是“当正好允许两个左移时”,这意味着在横向移动时不能连续左移两次,也就是说,只能有一次左移。
该问题可以使用动态规划来解决。首先,我们定义一个二维数组 $dp$,其中 $dp_{i,j}$ 表示从起点到 $(i,j)$ 这个格子的最大路径总和。那么,$dp_{i,j}$ 可以从 $dp_{i-1,j}$ 和 $dp_{i,j-1}$ 转移而来。具体转移方程如下:
$$ dp_{i,j} = \max(dp_{i-1,j}, dp_{i,j-1}) + a_{i,j} $$
其中,$a_{i,j}$ 表示 $(i,j)$ 这个格子的值。
需要注意的是,由于题目要求不能连续左移两次,我们需要对状态转移方程做出一些修改,具体来说,当 $i \geq 2$ 且 $j = 1$ 时,$dp_{i,j}$ 的值应该从 $dp_{i-2,m}$($m$ 为最大列数)转移而来。转移方程如下:
$$ dp_{i,j} = \max(dp_{i-1,j}, dp_{i,j-1}) + a_{i,j} \ (j \neq 1) \ dp_{i,j} = \max(dp_{i-1,j}, dp_{i-2,m}) + a_{i,j} \ (j = 1 \ \mathrm{and} \ i \geq 2) $$
最终,最大路径总和就是 $dp_{n,m}$($n$ 为最大行数,$m$ 为最大列数)。
下面是 Python 语言的动态规划的实现:
def maxPathSum(matrix):
n, m = len(matrix), len(matrix[0])
dp = [[0] * m for _ in range(n)]
dp[0][0] = matrix[0][0]
for i in range(1, n):
if i == 1:
dp[i][0] = matrix[i][0] + dp[i-1][0]
else:
dp[i][0] = matrix[i][0] + max(dp[i-1][0], dp[i-2][m-1])
for j in range(1, m):
dp[0][j] = matrix[0][j] + dp[0][j-1]
for i in range(1, n):
if j == 1:
dp[i][j] = matrix[i][j] + max(dp[i-1][j], dp[i][j-1])
else:
dp[i][j] = matrix[i][j] + max(dp[i-1][j], dp[i][j-1])
return dp[n-1][m-1]
该函数的输入参数为一个二维矩阵,输出最大路径总和。
需要注意的是,代码中的 $n$ 和 $m$ 对应题目中的最大行数和最大列数,而 $i$ 和 $j$ 从 $0$ 开始取值,所以在转移方程中需要加 $1$。另外,由于 Python 的数组下标可以为负,所以我们并不需要特别处理 $j = 0$ 的情况。
由于我们需要遍历整个矩阵,所以时间复杂度是 $O(nm)$,其中 $n$ 和 $m$ 分别为矩阵的行数和列数。
由于我们需要维护一个二维数组 $dp$,所以空间复杂度是 $O(nm)$。
在2D矩阵中找到最大路径总和是一个经典的动态规划问题。对于这个问题,我们可以使用动态规划来解决。需要注意的是,题目中要求不能连续左移两次,因此,需要对状态转移方程做出相应的修改。实现时,我们需要遍历整个矩阵,并维护一个二维数组 $dp$。最终,最大路径总和就是 $dp_{n,m}$。时间复杂度是 $O(nm)$,空间复杂度是 $O(nm)$。