• 过河卒(递推和递归)


    #include <iostream>

    #include <cstdio>

    using namespace std;

    int d[25][25],n,m,cx,cy;

    long long dp[25][25];      //d数组用来记录是不是控制点(“马点”),dp数组用来记录路径数

    int dir[8][2]={{2,1},{1,2},{-1,2},{-2,1},{-2,-1},{-1,-2},{1,-2},{2,-1}};  //二维方向数组(将“马点”全部标记为1)

    //dp[n][m]就表示到坐标为(n,m)点的可能的路径总数

    void fun()

    {

        d[cx][cy]=1;   //马的初始位置(有马的地方标记为1)

        for(int i=0;i<8;i++)

        {

            int tx=cx+dir[i][0];

            int ty=cy+dir[i][1];

            if(tx>=0 && tx<=n && ty>=0 && ty<=m) //注意范围

                d[tx][ty]=1;        //有马的地方标记为1

        }

        dp[0][0]=1;     //不能把做这样的初始化:dp[1][0]=1; dp[0][1]=1;的原因在于:这两个点可能是“马点”

        for(int i=0;i<=n;i++)  //取等,因为需要算到坐标(n,m)

        {

            for(int j=0;j<=m;j++)//取等,因为需要算到坐标(n,m)

            {

                if(d[i][j]==0)//有马的地方不去(所以直接不算入)

                {

                    if(i!=0 && j!=0)

                        dp[i][j]+=dp[i][j-1]+dp[i-1][j];//左边或者上边有马时,这一边过来的方法按0计算(所以这里直接加就行,因为数组的初始化是0)

                    if(i==0)    //马只能往右或者往下

                        dp[i][j]+=dp[i][j-1];   //第一次循环时j-1是-1,没关系,反正dp初始化都是0

                    if(j==0)

                        dp[i][j]+=dp[i-1][j];

                }

            }

        }

        cout<<dp[n][m];

    }

     

    int main()

    {

        cin>>n>>m;

        cin>>cx>>cy;

        fun();

        return 0;

    }

    这篇文章,是又一个故事的结束...
    lazy's story is continuing.
  • 相关阅读:
    软件开发模型
    Java学习--数组
    10年软件测试经验
    Log4net
    文件下载界面
    VB.NET中文双引号的处理方法
    SOAPUI使用
    .net数字转换成汉字大写
    SQL调用Webservices
    SQL大小写金额转换
  • 原文地址:https://www.cnblogs.com/Hello-world-hello-lazy/p/13576450.html
Copyright © 2020-2023  润新知