今日题目
(困难,动态规划,记忆化搜索)
T329 矩阵中的最长递增路径
题目描述
给定一个整数矩阵,找出最长递增路径的长度。
对于每个单元格,你可以往上,下,左,右四个方向移动。 你不能在对角线方向上移动或移动到边界外(即不允许环绕)。
示例 1:
输入: nums =
[
[9,9,4],
[6,6,8],
[2,1,1]
]
输出: 4
解释: 最长递增路径为 [1, 2, 6, 9]。
示例 2:
输入:
nums =
[
[3,4,5],
[3,2,6],
[2,2,1]
]
输出: 4
解释: 最长递增路径是 [3, 4, 5, 6]。注意不允许在对角线方向上移动。
标签
动态规划,记忆化,深度优先搜索(DFS),有向图
解析
这道题官方给了两种解法:记忆化深度优先搜索,以及拓扑排序。官方题解的地址在这里:官方题解
C++解法
class Solution
{
public:
int rows, columns;
vector<vector<int>> data;
vector<vector<int>> res;
int dir[4][2] = {{1, 0}, {0, 1}, {-1, 0}, {0, -1}};
int calculate(int x, int y)
{
if (res[x][y] != 0)
{
return res[x][y];
}
for (int i = 0; i < 4; ++i)
{
int x1 = x + dir[i][0], y1 = y + dir[i][1];
if (x1 < 0 || x1 >= rows || y1 < 0 || y1 >= columns)
{
continue;
}
if (data[x1][y1] < data[x][y])
{
res[x][y] = max(res[x][y], calculate(x1, y1));
}
}
return ++res[x][y];
}
int longestIncreasingPath(vector<vector<int>> &matrix)
{
rows = matrix.size();
int ans = 0;
if (rows == 0)
{
return 0;
}
columns = matrix[0].size();
data = matrix;
res = vector<vector<int>>(rows, vector<int>(columns, 0));
for (int i = 0; i < rows; ++i)
{
for (int j = 0; j < columns; ++j)
{
if (res[i][j] == 0)
{
calculate(i, j);
}
ans = max(ans, res[i][j]);
}
}
return ans;
}
};
python解法
class Solution:
def longestIncreasingPath(self, matrix: List[List[int]]) -> int:
rows = len(matrix)
if rows == 0:
return 0
columns = len(matrix[0])
ans = 0
res = [[0] * columns for i in range(rows)]
dir = [(-1, 0), (1, 0), (0, -1), (0, 1)]
def calculate(x, y) -> int:
if res[x][y] != 0:
return res[x][y]
for i in range(4):
dx, dy = dir[i]
x1 = x + dx
x2 = y + dy
if x1 < 0 or x1 >= rows or y1 < 0 or y1 >= columns:
continue
if matrix[x1][y1] < matrix[x][y]:
res[x][y] = max(res[x][y], calculate(x1, y1))
res[x][y] += 1
return res[x][y]
for i in range(rows):
for j in range(columns):
if res[i][j] == 0:
calculate(i, j)
ans=max(ans,res[i][j])
return ans