【题目】
给定一个包含非负整数的 m x n 网格,请找出一条从左上角到右下角的路径,使得路径上的数字总和为最小。
说明:每次只能向下或者向右移动一步。
示例:
输入:
[
[1,3,1],
[1,5,1],
[4,2,1]
]
输出: 7
解释: 因为路径 1→3→1→1→1 的总和最小。
【思路】
这道题和上次分享的【20T29-不同路径 II】非常类似,也是动态规划题目。
递归公式是:dp[i][j] = min(dp[i - 1][j], dp[i][j - 1]) + grid[i][j]。
当然可以转换使用一维数组:dp[j] = min(dp[j], dp[j - 1]) + grid[i][j]。
【代码】
python版本
class Solution(object):
def minPathSum(self, grid):
"""
:type grid: List[List[int]]
:rtype: int
"""
# dp[i][j] = min(dp[i-1][j], dp[i][j-1])
if len(grid) == 0 or len(grid[0]) == 0:
return 0
dp = [grid[0][0]] * len(grid[0])
for j in range(1, len(grid[0])):
dp[j] = dp[j - 1] + grid[0][j]
for i in range(1, len(grid)):
dp[0] += grid[i][0]
for j in range(1, len(grid[0])):
dp[j] = min(dp[j - 1], dp[j]) + grid[i][j]
return dp[-1]
C++版本
class Solution {
public:
int minPathSum(vector<vector<int>>& grid) {
if(grid.size() == 0 || grid[0].size() == 0)
return 0;
vector<int> dp(grid[0].size(), grid[0][0]);
for (int j = 1; j < grid[0].size(); j++)
dp[j] = dp[j - 1] + grid[0][j];
for (int i = 1; i < grid.size(); i++) {
dp[0] = dp[0] + grid[i][0];
for (int j = 1; j < grid[0].size(); j++) {
dp[j] = min(dp[j - 1], dp[j]) + grid[i][j];
}
}
return dp.back();
}
};