LeetCode偶尔一题 —— 64. 最小路径和

题目描述

给定一个包含非负整数的 m x n 网格,请找出一条从左上角到右下角的路径,使得路径上的数字总和为最小。
说明:每次只能向下或者向右移动一步。 示例:javascript

输入:
[
[1,3,1],
[1,5,1],
[4,2,1]
]
输出: 7
解释: 由于路径 1→3→1→1→1 的总和最小。前端

分析题目

递归

对于有些题目,若是咱们一会儿想不出来解题思路,其实能够稍微对它分析一下,那么天然就会找到解题的办法。
根据题中描述,咱们知道每次只能向下或者向右移动一步,咱们以此为依据画出示例中全部可能的路径👇java

很明显这是一个树形结构,咱们只要算出每一个头结点叶子结点所通过的路径和,它们中最小的值就是题目中要求的最小路径和,所以咱们能够尝试用深度优先搜索来解决它,初版程序👇git

var minPathSum = function (grid) {
    return dfs(0, 0)
    function dfs (i, j) {
        if (i === grid.length || j === grid[0].length) {
            return Number.MAX_SAFE_INTEGER
        }
        if (i === grid.length - 1 && j === grid[0].length - 1) {
            return grid[i][j]
        }
        return grid[i][j] + Math.min(dfs(i + 1, j), dfs(i, j + 1))
    }
}
复制代码

动态规划

细心的你可能已经发现,这道题其实能够把它分解为一个个子问题,而咱们只要解决了子问题,那么只要把子问题合并起来就能给出解。
怎么说呢?原题目让咱们求到 grid[i][j] 的最小路径,那么咱们只要找到 grid[i][j]上一个或者左一个中和它加起来最小的一个。换成代码也就是求👉 min = Math.min(grid[i][j] + grid[i - 1][j], gird[i][j] + grid[i][j-1])github

具体实现以下👇微信

var minPathSum = function(grid) {
    let x = grid.length - 1, y = grid[0].length - 1
    for (let i = 0; i <= x; i++) {
        for (let j = 0; j <= y; j++) {
            let tmp = grid[i][j]
            if (j === 0) {
                if (i > 0) {
                    grid[i][j] = grid[i - 1][j] + tmp
                }
            } else {
                if (i > 0) {
                    grid[i][j] = Math.min(grid[i - 1][j] + tmp, grid[i][j - 1] + tmp)
                } else {
                    grid[i][j] = grid[i][j - 1] + tmp
                }
            }
        }
    }
    return grid[x][y]
};
复制代码

原题地址: leetcode-cn.com/problems/mi… 代码不定时更新,欢迎 star 个人 repoui

扫描下方的二维码或搜索「tony老师的前端补习班」关注个人微信公众号,那么就能够第一时间收到个人最新文章。 spa

相关文章
相关标签/搜索