Leecode No 576 出界的路径数

本文探讨了使用动态规划和记忆化搜索两种算法来寻找网格中从起点到终点的最短路径。动态规划方法通过填充一个三维数组来记录每一步到达每个位置的路径数量,而记忆化搜索则利用递归和缓存来避免重复计算。两种方法都以优化计算效率为目标,并在代码中展示了具体实现。
摘要由CSDN通过智能技术生成

 


动态规划  

#include<iostream>
#include<vector>
#include<string.h>
using namespace std;

int findPaths(int m, int n, int maxMove, int startRow, int startColumn) {
    const int mod=1000000007;
    vector<vector<vector<int>>> dp(maxMove + 1, vector<vector<int>>(m, vector<int>(n)));
   //k-第几步  (x,y)-位置   dp[k][x][y]表示经过k步到达x y的路径数
    dp[0][startRow][startColumn]=1;         //初始点经过0次可以到达
    int res=0;
    vector<vector<int>> direction={{0,1},{1,0},{-1,0},{0,-1}};          //上下左右四个方向
    for(int i=1; i<=maxMove ; i++)
    {
        for(int x=0 ; x<m ;x++)
        {
            for(int y=0 ; y<n ;y++)
            {
                int count=dp[i-1][x][y];        //遍历整个数组
                if(count!=0)                    //这里表示这个点在上一步时是可以到达的,
                {                               //如果在上一步也不能到达就没有讨论的必要
                    for(auto d : direction)     //从该点遍历四个方向
                    {
                        int _x=x+d[0],_y=y+d[1];    //新位置
                        if(_x>=0&&_x<m&&_y>=0&&_y<n)    //新位置还在网格内
                        {
                           dp[i][_x][_y]=(dp[i][_x][_y]+count)%mod; //该新位置可以到达的路径数 等于本身加上旧位置的路径数
                        }
                        else
                             res=(res+count)%mod;       // 出界了结果res加上旧位置的路径数
                    }
                }
            }
        }
    }
    return res;
}

记忆化搜索

const int mod=1000000007;
int MAX,_m,_n;
long int dp[51][51][51];
int dfs(int x,int y,int k)
{
    if(k>MAX) return 0;
    if(x<0||y<0||x>=_m||y>=_n) return 1;
    if(dp[x][y][k]!=-1) return dp[x][y][k];
    else  return dp[x][y][k]=dfs(x+1,y,k+1)+dfs(x-1,y,k+1)+dfs(x,y+1,k+1)+dfs(x,y-1,k+1)%mod;
}
int findPaths(int m, int n, int maxMove, int startRow, int startColumn) {
    memset(dp,-1,sizeof(dp));
    MAX=maxMove;
    _m=m;
    _n=n;
    return dfs(startRow,startColumn,0);
}
int main()
{
    cout<<findPaths(1,3,3,0,1);
    return 0;
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值