题目链接: leetcode.cn/problems/0i…
题目描述:
给定一个包含非负整数的 m x n 网格 grid ,请找出一条从左上角到右下角的路径,使得路径上的数字总和为最小。
说明: 一个机器人每次只能向下或者向右移动一步。
示例 1:
输入: grid = [[1,3,1],[1,5,1],[4,2,1]]
输出: 7
解释: 因为路径 1→3→1→1→1 的总和最小。
示例 2:
输入: grid = [[1,2,3],[4,5,6]]
输出: 12
提示:
m == grid.lengthn == grid[i].length1 <= m, n <= 2000 <= grid[i][j] <= 100
题目解析
又是一题动态规划,题目和之前的差别不大。
创建 dp[i][j] 表示在 i、j 下标处的数字总和(步数)。
题目中描述只能往右、正下方走,那么来时方向就只能是左方、正上方。我们只要判断左方的 dp 和正上方的 dp 值谁
dp[i][j] = Math.min(dp[i - 1][j], dp[i][j - 1]) + grid[i - 1][j - 1];
这题在创建 dp 表的时候我选择的是 int[][] dp = new int[m + 1][n + 1]; 预留空间,我们要将表格中的值初始化为不会影响我们结果的值,所以我们除了第一行的第二列和第一列的第二行不设置值(默认为 0)其他的所有值都设置为最大值。假设我们的 dp 表为 5 × 5,我们应该将表初始化如下图

代码
class Solution {
public int minPathSum(int[][] grid) {
int m = grid.length;
int n = grid[0].length;
int[][] dp = new int[m + 1][n + 1];
//初始化dp表
for (int i = 2; i <= n; i++) dp[0][i] = Integer.MAX_VALUE;
for (int i = 2; i <= m; i++) dp[i][0] = Integer.MAX_VALUE;
//开始填表
for (int i = 1; i <= m; i++) {
for (int j = 1; j <= n; j++) {
dp[i][j] = Math.min(dp[i - 1][j], dp[i][j - 1]) + grid[i - 1][j - 1];
}
}
return dp[m][n];
}
}