您的位置:首页 > 其它

hdu 3555 Bomb (数位dp入门)

2016-03-07 20:30 399 查看
http://acm.hdu.edu.cn/showproblem.php?pid=3555

数位dp(bfs版)

#include<iostream>
#include<cstring>
#include<algorithm>
using namespace std;

long long bit[64];
long long dp[64][2];

long long dfs(long long len,long long is4,long long p)
{
if (!len) return 1;
if (!p&&dp[len][is4]>=0) return dp[len][is4];
long long cut=0,i,mx=p ? bit[len] : 9;
for (i=0;i<=mx;i++)
{
if (is4&&i==9) continue;
cut+=dfs(len-1,i==4,p&&i==mx);
}
return p ? cut : dp[len][is4]=cut;
}
long long f(long long n)
{
long long len=0;
while (n)
{
bit[++len]=n%10;
n/=10;
}
memset(dp,-1,sizeof(dp));
return dfs(len,0,1);
}
int main()
{
long long t,n;
cin>>t;
while (t--)
{
cin>>n;
cout<<n-f(n)+1<<endl;
}
return 0;
}


数位dp

#include<iostream>
#include<cstring>
using namespace std;
long long dp[20][3];
long long n;
void Init()
{
long long i;
memset(dp,0,sizeof(dp));
dp[0][0]=1;
for (i=1;i<20;i++)
{
dp[i][0]=dp[i-1][0]*10-dp[i-1][1];
dp[i][1]=dp[i-1][0];
dp[i][2]=dp[i-1][2]*10+dp[i-1][1];
}
}
long long ans()
{
long long sum=0,s[20],l=0,flag=0;
while (n)
{
s[++l]=n%10;
n/=10;
}
s[l+1]=0;
for (;l;l--)
{
sum+=dp[l-1][2]*s[l];
if (flag) sum+=dp[l-1][0]*s[l];
else if (s[l]>4) sum+=dp[l-1][1];
if (s[l+1]==4 && s[l]==9) flag=1;
}
return sum;
}
int main()
{
long long t;
cin>>t;
while (t--)
{
cin>>n;
//   for (int i=1;i<5;i++)
//   cout<<dp[i][0]<<" "<<dp[i][1]<<" "<<dp[i][2]<<endl;
n+=1;
Init();
cout<<ans()<<endl;
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: