bzoj1833
Description
给定两个正整数a和b,求在[a,b]中的所有整数中,每个数码(digit)各出现了多少次。
Input
输入文件中仅包含一行两个整数a、b,含义如上所述。
Output
输出文件中包含一行10个整数,分别表示0-9在[a,b]中出现了多少次。
单独考虑每一位,数位dp,注意前导零
/**************************************************************
Problem: 1833
User: walfy
Language: C++
Result: Accepted
Time:72 ms
Memory:1356 kb
****************************************************************/
//#pragma comment(linker, "/stack:200000000")
//#pragma GCC optimize("Ofast,no-stack-protector")
//#pragma GCC target("sse,sse2,sse3,ssse3,sse4,popcnt,abm,mmx,avx,tune=native")
//#pragma GCC optimize("unroll-loops")
#include
#define fi first
#define se second
#define mp make_pair
#define pb push_back
#define pi acos(-1.0)
#define ll long long
#define vi vector
#define mod 1000000007
#define ld long double
#define C 0.5772156649
#define ls l,m,rt<<1
#define rs m+1,r,rt<<1|1
#define pil pair
#define pli pair
#define pii pair
#define cd complex
#define ull unsigned long long
#define base 1000000000000000000
#define fio ios::sync_with_stdio(false);cin.tie(0)
using namespace std;
const double eps=1e-6;
const int N=20000+10,maxn=500000+10,inf=0x3f3f3f3f,INF=0x3f3f3f3f3f3f3f3f;
int dight[20];
ll dp[20][20][10][2];
ll dfs(int id,int sum,int who,bool zero,int fp)
{
if(!id)
{
return sum;
}
if(!fp&&dp[id][sum][who][zero]!=-1)return dp[id][sum][who][zero];
int fpmax=fp?dight[id]:9;
ll ans=0;
for(int i=0;i<=fpmax;i++)
{
if(i==who&&zero)ans+=dfs(id-1,sum+1,who,zero|i,fp&&i==fpmax);
else ans+=dfs(id-1,sum,who,zero|i,fp&&i==fpmax);
}
if(!fp)dp[id][sum][who][zero]=ans;
return ans;
}
ll ans[10];
int main()
{
ll a,b;
scanf("%lld%lld",&a,&b);
memset(dp,-1,sizeof dp);
int cnt=0;
while(b)
{
dight[++cnt]=b%10;
b/=10;
}
ans[0]+=dfs(cnt,0,0,0,1);
for(int i=1;i<=9;i++)
ans[i]+=dfs(cnt,0,i,1,1);
a--;
if(a>=1)
{
memset(dp,-1,sizeof dp);
cnt=0;
while(a)
{
dight[++cnt]=a%10;
a/=10;
}
ans[0]-=dfs(cnt,0,0,0,1);
for(int i=1;i<=9;i++)
ans[i]-=dfs(cnt,0,i,1,1);
}
for(int i=0;i<9;i++)printf("%lld ",ans[i]);
printf("%lld\n",ans[9]);
return 0;
}
/********************
********************/