一道数位DP的板子题……
哈哈哈
xiangxi见代码
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
#define rep(i,a,b) for(long long i=a;i<=b;i++)
#define mod 1000000007
using namespace std;
typedef long long ll;
struct node
{
ll s[10],r,sum;
node operator +(node x)//重载+运算符,方便计算
{
x.s[0]+=s[0];
x.s[1]+=s[1];
x.s[2]+=s[2];
x.s[3]+=s[3];
x.s[4]+=s[4];
x.s[5]+=s[5];
x.s[6]+=s[6];
x.s[7]+=s[7];
x.s[8]+=s[8];
x.s[9]+=s[9];
x.sum+=sum;
return x;
}
node operator -(node x)//重载-运算符,方便计算
{
x.s[0]=s[0]-x.s[0];
x.s[1]=s[1]-x.s[1];
x.s[2]=s[2]-x.s[2];
x.s[3]=s[3]-x.s[3];
x.s[4]=s[4]-x.s[4];
x.s[5]=s[5]-x.s[5];
x.s[6]=s[6]-x.s[6];
x.s[7]=s[7]-x.s[7];
x.s[8]=s[8]-x.s[8];
x.s[9]=s[9]-x.s[9];
return x;
}
}dp[16][2];
ll power[106],m[106];
node dfs(ll t,ll b,ll z)//t表示此时记录到第t位,b表示此时是否可以记录b以下所有数(b=0则可以) ,z处理前导零
{
node ans;
rep(i,0,9) ans.s[i]=0;
ans.r=1;
ans.sum=0;
if(t==0)
{
ans.sum=1;
return ans;
}
if(dp[t][z].r!=-1 && !b) return dp[t][z];//采取记忆化搜索优化时间
ll en=b?m[t]:9;
rep(i,0,en)
{
node tmp=dfs(t-1,b&&i==en,z&&i==0);
ans=ans+tmp;
if((!z || i>0)) ans.s[i]+=tmp.sum;//sum表示第t位以下一共的数;
}
if(!b) dp[t][z]=ans;
return ans;
}
node cnt(ll a)
{
ll tot=0;
while(a)//分解数位
{
m[++tot]=a%10;
a/=10;
}
return dfs(tot,1,1);
}
int main()
{
ll a,b,n;
power[1]=1;
rep(i,2,15) power[i]=power[i-1]*10;
rep(i,1,16)
rep(j,0,1)
dp[i][j].r=-1;
scanf("%lld%lld",&a,&b);
node hh=cnt(b)-cnt(a-1);
rep(i,0,9)
{
if(i!=0) printf(" ");
printf("%lld",hh.s[i]);
}
}