看到路径问题,我第一个想到的就是dfs或者是bfs。
从一个点出发,寻找最长的递增路径,只需要向四周四个点进行探索,找出分别从四个点出发的最长的递增路径的最大值,之后+1就可。
朴素深度优先搜索的时间复杂度过高的原因是进行了大量的重复计算,同一个单元格会被访问多次,每次访问都要重新计算。由于同一个单元格对应的最长递增路径的长度是固定不变的,因此可以使用记忆化的方法进行优化。用矩阵 \text{memo}memo 作为缓存矩阵,已经计算过的单元格的结果存储到缓存矩阵中。
memo[i][j] = 1+ max{memo[i-1][j], memo[i+1][j], memo[i][j-1], memo[i][j+1] }
代码如下:
class Solution {
int[][] dirs = {{-1,0}, {1,0}, {0,-1}, {0,1}};
int rows;
int cols;
public int dfs(int[][] matrix, int row, int col, int[][] memo){
if(memo[row][col]!=0){
return memo[row][col];
}
int newRow, newCol;
for(int[] dir : dirs){
newRow = row + dir[0];
newCol = col + dir[1];
if(newRow >=0 && newRow < rows && newCol >=0 && newCol < cols && matrix[newRow][newCol] > matrix[row][col]){
memo[row][col] = Math.max(memo[row][col],dfs(matrix, newRow, newCol, memo));
}
}
memo[row][col]++;
return memo[row][col];
}
public int longestIncreasingPath(int[][] matrix) {
if(matrix == null || matrix.length == 0 || matrix[0].length == 0){
return 0;
}
System.out.println(matrix);
rows = matrix.length;
cols = matrix[0].length;
int[][] memo = new int[rows][cols];
for(int i=0; i<rows; i++){
for(int j=0; j<cols; j++){
memo[i][j]=0;
}
}
int ans = 1;
for(int i=0; i<rows; i++){
for(int j=0; j<cols; j++){
ans = Math.max(ans, dfs(matrix, i, j, memo));
}
}
return ans;
}
}