链接
数位DP
数位DP重点看分类讨论,注重每一位上数字。
题意:
从a-b中0-9分别出现多少次?
分析:
我们可以那x来分析:如果一共abcdef位,那么我们看c位,
- 前面可以取00~(ab-1) 这样垢面cdef就可以随便取,我们固定c位为我们要的数字,后面就有1000种所以一工 ab*1000种 ,这是我们要求的数字大于0,等于0的话我们会发现前面00是不能取的,所以就是 (ab-1)*1000
- 然后当前两位是ab时。
- 如果c>x(我们要的数字)那么后面就一共有1000种方案。
- 如果c=x 那么后面可选的是 (000~def)一共def+1种方案
- c<x 就是0种
#include <iostream>
#include <cstring>
#include <algorithm>
using namespace std;
int a[100];
int getnum(int l,int r){
int ans=0;
if(l<r) return 0;
for(int i=l;i>=r;i--){
ans=ans*10+a[i];
}
return ans;
}
int qpow(int a,int b){
int ans=1;
while(b){
if(b&1) ans=ans*a;
b>>=1;
a=a*a;
}
return ans;
}
int count(int n,int x){
if(n==0) return 0;
int len=0;
while(n){
a[++len]= n%10;
n=n/10;
}
int ans=0;
for(int i=len;i>=1;i--){
int num=getnum(len,i+1);///qianmian
int sum=qpow(10,(i-1));///houmian
if(num!=0){
ans+=sum * num;
if(x==0) ans-=sum;
}
if(a[i]>x){
if(i==len&&x==0) continue;
ans+=sum;
}
if(a[i]==x) {
ans+=getnum(i-1,1)+1;
}
}
return ans;
}
int main()
{
int n,m;
while (cin>>n>>m&&(n||m)){
if(n<m) swap(n,m);
for(int i=0;i<10;i++)
cout<<count(n,i)-count(m-1,i)<<' ';
cout<<endl;
}
return 0;
}