1. 程式人生 > >Pascal's Travels HDU

Pascal's Travels HDU

An n x n game board is populated with integers, one nonnegative integer per square. The goal is to travel along any legitimate path from the upper left corner to the lower right corner of the board. The integer in any one square dictates how large a step away from that location must be. If the step size would advance travel off the game board, then a step in that particular direction is forbidden. All steps must be either to the right or toward the bottom. Note that a 0 is a dead end which prevents any further progress. 


Consider the 4 x 4 board shown in Figure 1, where the solid circle identifies the start position and the dashed circle identifies the target. Figure 2 shows the three paths from the start to the target, with the irrelevant numbers in each removed. 


Figure 1


Figure 2
InputThe input contains data for one to thirty boards, followed by a final line containing only the integer -1. The data for a board starts with a line containing a single positive integer n, 4 <= n <= 34, which is the number of rows in this board. This is followed by n rows of data. Each row contains n single digits, 0-9, with no spaces between them. 
OutputThe output consists of one line for each board, containing a single integer, which is the number of paths from the upper left corner to the lower right corner. There will be fewer than 2^63 paths for any board. 
Sample Input
4
2331
1213
1231
3110
4
3332
1213
1232
2120
5
11101
01111
11111
11101
11101
-1
Sample Output
3
0
7


        
 
Brute force methods examining every path will likely exceed the allotted time limit. 
64-bit integer values are available as "__int64" values using the Visual C/C++ or "long long" values 
using GNU C/C++ or "int64" values using Free Pascal compilers. 
Hint
Hint

這道題意思是 一個n x n遊戲板填充整數,一個非負整數每平方。目標是沿著從左上角到右下角的任何合法路線行進。任何一個方塊中的整數決定了距離該位置的距離有多大。如果步距大大提升遊戲板的距離,那麼禁止這個特定方向的步驟。所有步驟必須在右側或底部。請注意,0是一個死衚衕,防止任何進一步的進展。
考慮圖1所示的4 x 4板,其中實心圓標識起始位置,虛線圓標識目標。圖2顯示了從起始到目標的三個路徑,每個路徑中的不相關數字被刪除。
輸入包含一到三十個單板的資料,後跟一個僅包含整數-1的最後一行。電路板的資料以包含單個正整數n的行開始,4 <= n <= 34,即該單板中的行數。這之後是n行資料。每行包含n個單數位,0-9,它們之間沒有空格。
輸出由每個單板的一行組成,包含一個整數,即從左上角到右下角的路徑數。任何董事會將不到2 ^ 63個路徑  

                                       

方法1:2代表它只能向右走2步或向下走2步,用dp用來儲存路徑,最後輸出dp[n-1][n-1]即可。

方法2:用深搜做if(dp[x][y]  ||  a[x][y]==0)      return dp[x][y],    

dp[x][y]+=dfs(x+a[x][y],y)  dp[x][y]+=dfs(x,y+a[x][y]);

方法1:


#include<stdio.h>
#include<string.h>
char a[50][50];
__int64 dp[100][100];
int main()
{
    int n,i,j;
    while(~scanf("%d",&n)&&n!=-1)
    {
        memset(dp,0,sizeof(dp));
        for(i=0; i<n; i++)
            scanf("%s",a[i]);
        dp[0][0]=1;
        for(i=0; i<n; i++)
        {
            for(j=0; j<n; j++)
            {
                int t=a[i][j]-'0';
                if(i==n-1&&j==n-1)
                    break;
                dp[i+t][j]+=dp[i][j];//向右
                dp[i][j+t]+=dp[i][j];//向下
            }
        }
        printf("%I64d\n",dp[n-1][n-1]);
    }
    return 0;
}

方法2:
#include<stdio.h> #include<string.h> __int64 dp[50][50]; int a[50][50],n; __int64 dfs(int x,int y) { if(x<0||y<0||x>=n||y>=n) return 0; if(dp[x][y]||a[x][y]==0) return dp[x][y]; dp[x][y]+=dfs(x+a[x][y],y); dp[x][y]+=dfs(x,y+a[x][y]); return dp[x][y]; } int main() { while(~scanf("%d",&n)&&n!=-1) { int i,j; memset(dp,0,sizeof(dp)); for(i=0; i<n; i++) for(j=0; j<n; j++) scanf("%1d",&a[i][j]); dp[n-1][n-1]=1; printf("%lld\n",dfs(0,0)); } return 0; }