算法leetcode|63. 不同路径 II(rust重拳出击)


文章目录


63. 不同路径 II:

一个机器人位于一个 m x n 网格的左上角 (起始点在下图中标记为 "Start" )。

机器人每次只能向下或者向右移动一步。机器人试图达到网格的右下角(在下图中标记为 "Finish")。

现在考虑网格中有障碍物。那么从左上角到右下角将会有多少条不同的路径?

网格中的障碍物和空位置分别用 10 来表示。

样例 1:

复制代码
输入:
	
	obstacleGrid = [[0,0,0],[0,1,0],[0,0,0]]
	
输出:
	
	2
	
解释:

	3x3 网格的正中间有一个障碍物。
	从左上角到右下角一共有 2 条不同的路径:
	1. 向右 -> 向右 -> 向下 -> 向下
	2. 向下 -> 向下 -> 向右 -> 向右

样例 2:

复制代码
输入:
	
	obstacleGrid = [[0,1],[0,0]]
	
输出:
	
	1

提示:

  • m == obstacleGrid.length
  • n == obstacleGridi.length
  • 1 <= m, n <= 100
  • obstacleGridij 为 0 或 1

分析:

  • 面对这道算法题目,二当家的再次陷入了沉思。
  • 这道题和62. 不同路径 类似,但是由于有随机位置的障碍物,所以就不能直接用数学的组合数方式求解了。
  • 那么动态规划成了此时的优选。每一个点的不同路径数是到达上面点的不同路径数与到达左面不同路径数的和。我们可以按行从上到下的方式处理(按列从左到右处理也是可以的,但是有些别扭,因为二维数组的第一维是行,第二维是列,习惯上都是按行处理),这样会发现每行只和上一行的结果有关系,所以就不需要 m * n 的额外空间,而只需要 m 的空间,即滚动数组的思想。

题解:

rust:

rust 复制代码
impl Solution {
    pub fn unique_paths_with_obstacles(obstacle_grid: Vec<Vec<i32>>) -> i32 {
        let rows = obstacle_grid.len();
        let cols = obstacle_grid[0].len();
        let mut dp = vec![0; cols];

        if obstacle_grid[0][0] == 0 {
            dp[0] = 1;
        }

        (0..rows).for_each(|r| {
            (0..cols).for_each(|c| {
                if obstacle_grid[r][c] == 1 {
                    dp[c] = 0;
                } else if c > 0 && obstacle_grid[r][c - 1] == 0 {
                    dp[c] += dp[c - 1];
                }
            });
        });

        return dp[cols - 1];
    }
}

go:

go 复制代码
func uniquePathsWithObstacles(obstacleGrid [][]int) int {
    rows, cols := len(obstacleGrid), len(obstacleGrid[0])
	dp := make([]int, cols)

	if obstacleGrid[0][0] == 0 {
		dp[0] = 1
	}

	for r := 0; r < rows; r++ {
		for c := 0; c < cols; c++ {
			if obstacleGrid[r][c] == 1 {
				dp[c] = 0
				continue
			}
			if c > 0 && obstacleGrid[r][c-1] == 0 {
				dp[c] += dp[c-1]
			}
		}
	}

	return dp[cols-1]
}

c++:

cpp 复制代码
class Solution {
public:
    int uniquePathsWithObstacles(vector<vector<int>>& obstacleGrid) {
        const int rows = obstacleGrid.size(), cols = obstacleGrid.at(0).size();
        vector<int> dp(cols);

        dp[0] = (obstacleGrid[0][0] == 0);
        for (int r = 0; r < rows; ++r) {
            for (int c = 0; c < cols; ++c) {
                if (obstacleGrid[r][c] == 1) {
                    dp[c] = 0;
                    continue;
                }
                if (c > 0 && obstacleGrid[r][c - 1] == 0) {
                    dp[c] += dp[c - 1];
                }
            }
        }

        return dp.back();
    }
};

python:

python 复制代码
class Solution:
    def uniquePathsWithObstacles(self, obstacleGrid: List[List[int]]) -> int:
        rows, cols = len(obstacleGrid), len(obstacleGrid[0])
        dp = [0] * cols
        if obstacleGrid[0][0] == 0:
            dp[0] = 1
        for r in range(rows):
            for c in range(cols):
                if obstacleGrid[r][c] == 1:
                    dp[c] = 0
                    continue
                if c > 0 and obstacleGrid[r][c - 1] == 0:
                    dp[c] += dp[c - 1]
        return dp[cols - 1]

java:

java 复制代码
class Solution {
    public int uniquePathsWithObstacles(int[][] obstacleGrid) {
        final int   rows = obstacleGrid.length, cols = obstacleGrid[0].length;
        final int[] dp   = new int[cols];

        if (obstacleGrid[0][0] == 0) {
            dp[0] = 1;
        }

        for (int i = 0; i < rows; ++i) {
            for (int j = 0; j < cols; ++j) {
                if (obstacleGrid[i][j] == 1) {
                    dp[j] = 0;
                    continue;
                }
                if (j > 0 && obstacleGrid[i][j - 1] == 0) {
                    dp[j] += dp[j - 1];
                }
            }
        }

        return dp[cols - 1];
    }
}

非常感谢你阅读本文~

欢迎【点赞】【收藏】【评论】三连走一波~

放弃不难,但坚持一定很酷~

希望我们大家都能每天进步一点点~

本文由 二当家的白帽子:https://le-yi.blog.csdn.net/ 博客原创~


相关推荐
码少女18 小时前
数据结构——冒泡排序及优化
数据结构·算法·排序算法
神奇小汤圆18 小时前
Redis 哨兵搭建+ACL权限控制
后端
梦回江东18 小时前
ansible中的主机清单
算法
青梅橘子皮18 小时前
string---入门OJ题(1)
数据结构·算法
qq_4542450318 小时前
BasicMethod.Map 设计框架:8 个并行基础模块的数学根基与实现
数据结构·算法·c#
青山木18 小时前
Hot 100 --- 二叉树与递归
java·数据结构·算法·leetcode·深度优先
大型UFO19 小时前
在 Hermes Agent 里搭建全中文 Honcho 记忆系统踩过的坑
后端
花褪残红青杏小19 小时前
Rust图像处理第16节-曼德博集合 Mandelbrot:用一行公式画出无限细节
rust·webassembly·图形学
Arman376819 小时前
rusty-cat × 阿里云 OSS 直传直下实战
rust·ai编程
前端工作日常19 小时前
我学习到的Java概念
java·后端