Top 100 Linked Question 修炼------第64题

64. Minimum Path Sum

题目连接

题目意思:给出一个m*n的方格,方格里面的元素是非负数,现在要求你找一条路径,使得从[0][0]到[m-1][n-1]的路径长度最短。官方给出的例子如下:

Input:
[
  [1,3,1],
  [1,5,1],
  [4,2,1]
]
Output: 7

根据上面给出的解释,那么我们可以发现从左上到右下的一条最短的路径为(1→3→1→1→1),他们相加的和为7,这就是最短路径。

题目分析:分析这个题目的意思,是需要求解最短的路径(PS:一般出现最小或者最大的这个字眼的时候,都是采用动态规划),那么一般情况下是采用动态规划去解决,动态规划要求利用到上一次的结果,是一种特殊的迭代思想,动态规划的关键是要得到递推关系式。对于本题,从原点到达(i, j)的最小路径等于 :原点到达(i-1, j)最小路径与到达(i, j-1)最小路径中的最小值。即 dp[i][j] = Math.min(dp[i-1][j], dp[i][j-1])+nums[i][j].一般的情况下是写出基本的方案,然后后面再采取优化,先给出基本的动态规划的解题方案:

方案1:基本的解题方案(空间复杂度为O(m*n))

public int minPathSum(int[][] grid) {
    // 计算行数
    int m = grid.length;
    if(m==0) 
        return 0;
    //计算列数
    int n = grid[0].length;
    if(n==0) 
        return 0;
    int[][] f = new int[m][n];
    f[0][0] = grid[0][0];
    // 初始化行
    for(int i=1;i<m;i++) {
          f[i][0] = f[i-1][0] + grid[i][0];
    }
    // 初始化列
    for(int j=1;j<n;j++) {
          f[0][j] = f[0][j-1] + grid[0][j];
    }
    // 求解最短路径
    for(int i=1;i<m;i++) {
          for(int j=1;j<n;j++) {
                 f[i][j] = Math.min(f[i-1][j], f[i][j-1]) + grid[i][j];
          }
    }
    return f[m-1][n-1];
}

方案二:优化空间复杂度,使其空间复杂度降低为O(n)

    def minPathSum(self, grid):
        if not grid:
            return 0
        r,c=len(grid),len(grid[0])
        cur=[0]*c
        cur[0]=grid[0][0]
        # 初始化工作
        for i in range(1,c):
            cur[i]=cur[i-1]+grid[0][i]
        # DP
        for i in range(1,r):
            cur[0]+=grid[i][0]
            for j in range(1,c):
                cur[j]=min(cur[j-1],cur[j])+grid[i][j]
        return cur[-1]

PS:自己多动手写几遍DP,从最基本的开始,然后优化,多写几次就能掌握,勤能补拙,加油。

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值