Leetcode-Unique Paths&Unique PathsII

本文探讨了两种场景下机器人从起点到终点的不同路径计数方法。第一种是在无障碍物的网格中寻找唯一路径的数量,第二种则增加了障碍物,需绕过这些障碍物找到可达路径的数量。文章提供了详细的算法思路及实现代码。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Problem

Unique Paths

A robot is located at the top-left corner of a m x n grid (marked ‘Start’ in the diagram below).

The robot can only move either down or right at any point in time. The robot is trying to reach the bottom-right corner of the grid (marked ‘Finish’ in the diagram below).

How many possible unique paths are there?
Note: m and n will be at most 100.
具体详见Leetcode

Unique PathsII

Follow up for “Unique Paths”:

Now consider if some obstacles are added to the grids. How many unique paths would there be?

An obstacle and empty space is marked as 1 and 0 respectively in the grid.

For example,
There is one obstacle in the middle of a 3x3 grid as illustrated below.

[
[0,0,0],
[0,1,0],
[0,0,0]
]

The total number of unique paths is 2.

Note: m and n will be at most 100.
具体详见Leetcode

Analysis

算法

Unique Paths

每一个格子有两个行进方向,它只能从右边或者下面到达下一个格子,然后不管怎么走,终点是右下角的那个格子。所以,我们可以从右下角格子反走到左上角。从右下角出发,当前的方法数初始值为1,然后从这个格子出发,每个格子的方法数是它右边和下面的格子的方法数的总和,一直到(0,0)。
f[i][j] 为在i行j列的格子走到右下角的格子的方法数。
f[i][j]=f[i+1][j]+f[i][j+1]
最后的答案是 f[0][0]

Complexity

时间复杂度: O(n2)
空间复杂度: O(n2)

Unique PathsII

与上一题不同的是,这道题还加了障碍,矩阵中元素的值为1的就是障碍,障碍是不能通过的。首先还是让右下角的格子方法数为1(在它不为1的情况下,如果它为1,则永远不可能到达终点,所以方法数为0),当前格子的路径数为:下面格子的路径数(当右边格子为障碍时);右边格子的路径数(当下面格子为障碍时);两边格子的路径数之和;-1(下面的格子和右边的格子都有障碍)。
状态转移方程和上题一致,但是还要加入条件判断。最后如果(0,0)处的方法数算出来是-1,则说明终点不可达,返回路径数为0。

Complexity

时间复杂度: O(n2)
空间复杂度: O(n2)

Code

Unique Paths

class Solution {
public:
    int uniquePaths(int m, int n) {
        int** matrix = new int*[m];
        for (int i = 0; i < m; i++) {
            matrix[i] = new int[n];
        }
        for (int i = m  - 1; i >= 0; i--) {
            for (int j = n - 1; j >= 0; j--) {
                int r1 = i + 1;
                int c1 = j + 1;
                if (r1 >= m && c1 >= n) matrix[i][j] = 1;
                else if (r1 >= m) matrix[i][j] = matrix[i][c1];
                else if (c1 >= n) matrix[i][j] = matrix[r1][j];
                else matrix[i][j] = matrix[i][c1] + matrix[r1][j];
            }
        }
        int answer = matrix[0][0];
        for (int i = 0; i < m; i++) {
            delete matrix[i];
        }
        delete matrix;
        return answer;
    }
};

Unique PathsII

class Solution {
public:
    int uniquePathsWithObstacles(vector<vector<int>>& obstacleGrid) {
        int m = obstacleGrid.size();
        if (m == 0) return 0;
        int n = obstacleGrid[0].size();
        if (n == 0) return 0;
        if (obstacleGrid[m-1][n-1] == 1) return 0;
        int** matrix = new int*[m];
        for (int i = 0; i < m; i++) {
            matrix[i] = new int[n];
        }
        for (int i = m  - 1; i >= 0; i--) {
            for (int j = n - 1; j >= 0; j--) {

                int r1 = i + 1;
                int c1 = j + 1;
                if (r1 >= m && c1 >= n) matrix[i][j] = 1;
                else if (r1 >= m) matrix[i][j] = matrix[i][c1];
                else if (c1 >= n) matrix[i][j] = matrix[r1][j];
                else if (matrix[r1][j] == -1) matrix[i][j] = matrix[i][c1];
                else if (matrix[i][c1] == -1) matrix[i][j] = matrix[r1][j];
                else matrix[i][j] = matrix[i][c1] + matrix[r1][j];

                if (obstacleGrid[i][j] == 1) matrix[i][j] = -1;
            }
        }
        int answer = matrix[0][0];
        if (answer == -1) answer = 0;
        for (int i = 0; i < m; i++) {
            delete matrix[i];
        }
        delete matrix;
        return answer;
    }
};
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值