Codeforces Beta Round #2B(dp+数学)

贡献了一列WA。。

数学很神奇啊 

这个题的关键是怎么才能算尾0的个数 只能相乘 可以想一下所有一位数相乘 除0之外,只有2和5相乘才能得到0 当然那些本身带0的多位数 里面肯定含有多少尾0 就含有多少对2和5

这样就知道了 就是求2和5 的对数最少的 一条路 DP就不用说了 递推

注意有0的时候的计算  特殊处理一下

  1 #include <iostream>
  2 #include<cstdio>
  3 #include<cstring>
  4 #include<algorithm>
  5 #include<stdlib.h>
  6 #include<vector>
  7 using namespace std;
  8 #define N 1010
  9 #define INF 1e10
 10 #define LL __int64
 11 LL dp[N][N][2];
 12 int a[N][N],b[N][N];
 13 int n;
 14 char pa[N<<1];
 15 int init(int x,int k)
 16 {
 17     int num=0;
 18     while(x)
 19     {
 20         if(x%k==0)
 21         {
 22             num++;
 23             x/=k;
 24         }
 25         else break;
 26     }
 27     return num;
 28 }
 29 int main()
 30 {
 31     int i,j,y,o1,o2,f=0;
 32     scanf("%d",&n);
 33     for(i = 1; i <= n ; i++)
 34         for(j = 1; j <= n ; j++)
 35         {
 36             scanf("%d",&y);
 37             if(y==0)
 38             {
 39                 o1 = i;
 40                 o2 = j;
 41                 f = 1;
 42             }
 43             int o = init(y,2);
 44             a[i][j] = o;
 45             o = init(y,5);
 46             b[i][j] = o;
 47         }
 48     for(i = 0; i <= n; i++)
 49         for(j = 0; j <= n ; j++)
 50         {
 51             dp[i][j][0] = INF;
 52             dp[i][j][1] = INF;
 53         }
 54     dp[1][1][0] = a[1][1];
 55     dp[1][1][1] = b[1][1];
 56     for(i = 1; i <= n ; i++)
 57         for(j = 1; j <= n ; j++)
 58         {
 59             dp[i][j][0] = min(dp[i][j][0],min(dp[i-1][j][0],dp[i][j-1][0])+a[i][j]);
 60             dp[i][j][1] = min(dp[i][j][1],min(dp[i-1][j][1],dp[i][j-1][1])+b[i][j]);
 61         }
 62     int g = 0;
 63     if(f&&min(dp[n][n][0],dp[n][n][1])>1)
 64     {
 65         printf("1\n");
 66         for(i = 1; i < o2 ; i++)
 67         printf("R");
 68         for(i = 1; i < o1 ; i++)
 69         printf("D");
 70         for(i = o2; i < n ; i++)
 71         printf("R");
 72         for(i = o1; i < n ; i++)
 73         printf("D");
 74         return 0;
 75     }
 76     if(dp[n][n][0]<dp[n][n][1])
 77     {
 78         int i = n,j = n;
 79         while(1)
 80         {
 81             if(i>1&&dp[i][j][0]==dp[i-1][j][0]+a[i][j])
 82             {
 83                 i = i-1;
 84                 pa[++g] = 'D';
 85             }
 86             else if(j>1)
 87             {
 88                 j = j-1;
 89                 pa[++g] = 'R';
 90             }
 91             if(i==1&&j==1)
 92             break;
 93         }
 94     }
 95     else
 96     {
 97         int i = n,j = n;
 98         while(1)
 99         {
100             if(i>1&&dp[i][j][1]==dp[i-1][j][1]+b[i][j])
101             {
102                 i = i-1;
103                 pa[++g] = 'D';
104             }
105             else if(j>1)
106             {
107                 j = j-1;
108                 pa[++g] = 'R';
109             }
110             if(i==1&&j==1)
111             break;
112         }
113     }
114     printf("%I64d\n",min(dp[n][n][0],dp[n][n][1]));
115     for(i = g ; i >= 1 ; i--)
116     printf("%c",pa[i]);
117     puts("");
118     return 0;
119 }
View Code

posted @ 2013-10-21 17:01  _雨  阅读(271)  评论(0编辑  收藏  举报