您的位置:首页 > 其它

hdu 3555(数位dp)

2014-04-16 12:54 309 查看
//数位dp很有用要好好掌握

#include<stdio.h>

#include<string.h>

__int64 dp[30][10][k];//dp[i][j][2]表示i位首位为j(k==1 表示包含49 k=0 表示不包含49)的数有多少个

void build()

{

__int64 i,j,k;

memset(dp,0,sizeof(dp));

dp[0][0][0]=1;

for(i=1;i<=20;i++)

{

for(j=0;j<10;j++)

{

for(k=0;k<10;k++)

{

if(j==4&&k==9)//如果当前位为4 下一位为9 即出现49 则dp[i-1][j][0]也需要加到dp[i][j][1]中

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

else

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

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

}

}

}

}

__int64 get(__int64 x)

{

__int64 digit[30],len=0,i,f=0,j;

memset(digit,0,sizeof(digit));//必须初始化不然就错了 我也不知道为什么

while(x>0)

{

digit[++len]=x%10;

x=x/10;

}

i=len;

__int64 ans=0;

for(i=len;i>0;i--)

{

for(j=0;j<digit[i];j++)

{

if(f)

ans+=dp[i][j][0];

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

}

if(digit[i]==9&&digit[i+1]==4)f=1;

}

if(f)ans++;//x也包含49需要加入

return ans;

}

int main()

{

__int64 t;

__int64 n;

build();

scanf("%I64d",&t);

while(t--)

{

scanf("%I64d",&n);

printf("%I64d\n",get(n));

}

return 0;

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: