鱼C论坛

 找回密码
 立即注册
查看: 136|回复: 1

动态规划求解不同路径

[复制链接]
发表于 2024-10-23 09:52:38 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
题目描述:
一个机器人位于一个 m x n 网格的左上角 (起始点在下图中标记为 “Start” )。

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

问总共有多少条不同的路径?
代码在下面:
class Solution(object):
    def uniquePaths(self, m, n):
        """
        :type m: int
        :type n: int
        :rtype: int
        """
        # 采用二位数组形式的动态规划
        # f[i][j]表示当前移动到的总次数,要求f[-1][-1]
        # 状态转移公式:f[i][j] = f[i-1][j]+f[i][j-1]
        # 初始值:每一步移动的次数可以看做横轴和纵轴的和,因此 f[i][0] = 1,f[0][j]=1
        # 运动的轨迹:要么往下,要么往左
        # 时间复杂度:O(m*n),空间复杂度:O(m*n)
        
        f = [[0]*n for zong in range(m)]
        for i in range(m):
            f[i][0] = 1
        for j in range(n):
            f[0][j] = 1
        for i in range(1,m):
            for j in range(1,n):
                f[i][j] = f[i-1][j]+f[i][j-1]
        return f[-1][-1]
        

        """优化空间复杂度为O(n)"""
        # 对二维矩阵进行压缩成一位数组,将最新生成的值覆盖掉旧的值,逐行求解当前位置的最新路径条数!
        # 实质:在于动态计算并替换当前位置下的路径数最新值
        # 状态转移公式变成:f[i] = f[i-1]+f[i]
        # 初始值: f = [1]*m,取横轴
        # f[-1]表示可能路径的总数
        # 空间复杂度:O(n),时间复杂度:O(m*n)

        f = [1]*m
        for j in range(1,n):
            for i in range(1,m):
                f[i] = f[i-1]+f[i]
        return f[-1]
不明白的是为什么dp[-1][-1]能表示到最右下角的格子的最多路径?上段代码中如何体现最多路径数
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2024-10-23 10:10:56 | 显示全部楼层
在这个问题中,动态规划(DP)是一种有效的方法来计算从起点到终点的不同路径数。我们可以通过构建一个二维数组 `dp` 来解决这个问题,其中 `dp[i][j]` 表示从起点到达位置 `(i, j)` 的路径总数。

### 动态规划的思路:

1. **初始化**:
   - 由于机器人只能向右或向下移动,因此第一行和第一列的路径数都是 1。因为在第一行中,机器人只能一直向右移动;在第一列中,机器人只能一直向下移动。

2. **状态转移方程**:
   - 对于其他位置 `(i, j)`,路径数等于从上方到达该位置的路径数加上从左侧到达该位置的路径数,即:
     \[
     dp[i][j] = dp[i-1][j] + dp[i][j-1]
     \]

3. **最终结果**:
   - 右下角的格子 `dp[m-1][n-1]` 就是从起点到终点的不同路径总数。

### 代码实现:

以下是一个正确的动态规划实现:
class Solution(object):
    def uniquePaths(self, m, n):
        # 创建一个 m x n 的二维数组,并初始化为 0
        dp = [[0] * n for _ in range(m)]
        
        # 初始化第一行和第一列
        for i in range(m):
            dp[i][0] = 1
        for j in range(n):
            dp[0][j] = 1
        
        # 填充 dp 数组
        for i in range(1, m):
            for j in range(1, n):
                dp[i][j] = dp[i-1][j] + dp[i][j-1]
        
        # 返回右下角的值
        return dp[m-1][n-1]

### 解释:

- **初始化**:`dp[i][0]` 和 `dp[0][j]` 都被初始化为 1,因为在这些位置上只有一种路径。
- **状态转移**:通过 `dp[i][j] = dp[i-1][j] + dp[i][j-1]`,我们可以逐步计算出每个位置的路径数。
- **结果**:`dp[m-1][n-1]` 是最终的答案,表示从起点到终点的路径总数。

通过这种方法,我们可以有效地计算出从起点到终点的所有可能路径数。

以上回复来自 FishC AI 小助理,如未能正确解答您的问题,请继续追问。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-12-22 13:16

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表