您的位置:首页 > 其它

[数位DP] BZOJ 4521 [Cqoi2016]手机号码

2016-04-18 18:49 549 查看
题解:http://www.cnblogs.com/ccz181078/p/5379967.html

数位DP和喜闻乐见的前缀和

#include<cstdio>
#include<cstdlib>
#include<algorithm>
using namespace std;
typedef long long ll;

inline char nc()
{
static char buf[100000],*p1=buf,*p2=buf;
if (p1==p2) { p2=(p1=buf)+fread(buf,1,100000,stdin); if (p1==p2) return EOF; }
return *p1++;
}

inline void read(ll &x){
char c=nc(),b=1;
for (;!(c>='0' && c<='9');c=nc()) if (c=='-') b=-1;
for (x=0;c>='0' && c<='9';x=x*10+c-'0',c=nc()); x*=b;
}

ll L,R;
ll f[15][10][3][2][2][2];

inline ll Calc(ll x){
int num[16],p=0;
ll ret=0,itmp=x;
while (itmp) num[++p]=itmp%10,itmp/=10;
for (int i=1;i<p;i++)
for (int j=1;j<10;j++)
for (int a=0;a<3;a++)
ret+=f[i][j][a][1][0][0]+f[i][j][a][1][1][0]+f[i][j][a][1][0][1];
for(int i=1;i<num[p];i++)
for(int a=0;a<3;a++)
ret+=f[p][i][a][1][0][0]+f[p][i][a][1][0][1]+f[p][i][a][1][1][0];
int p1=num[p],p2=0;
int d4=p1==4,d8=p1==8,l3=0;
for(int i=p-1;i;i--){
for(int j=0;j<num[i];j++)
{
for(int a=0;a<3;a++)
{
ret+=f[i][j][a][1][0][0];
if(!d4)ret+=f[i][j][a][1][0][1];
if(!d8)ret+=f[i][j][a][1][1][0];
if(l3){
ret+=f[i][j][a][0][0][0];
if(!d4)ret+=f[i][j][a][0][0][1];
if(!d8)ret+=f[i][j][a][0][1][0];
}
}
if(l3)continue;
if(p1==j){
ret+=f[i][j][1][0][0][0];
if(!d4)ret+=f[i][j][1][0][0][1];
if(!d8)ret+=f[i][j][1][0][1][0];
if(p1==p2)
{
ret+=f[i][j][0][0][0][0];
if(!d4)ret+=f[i][j][0][0][0][1];
if(!d8)ret+=f[i][j][0][0][1][0];
}
}
}
if(p1==p2 && p1==num[i]) l3=1;
p2=p1; p1=num[i];
if(p1==4) { if(d8) break; d4=1; }
if(p1==8) { if(d4) break; d8=1; }
}
return ret;
}

int main()
{
freopen("t.in","r",stdin);
freopen("t.out","w",stdout);
for (int i=0;i<10;i++) f[1][i][0][0][i==4][i==8]=1;
for (int i=2;i<=12;i++)
for (int j=0;j<10;j++)
for (int k=0;k<10;k++)
for (int d4=0;d4<2;d4++)
for (int d8=0;d8<2;d8++)
if (j!=k)
{
for (int w=0;w<3;w++)
{
f[i][j][0][0][d4||j==4][d8||j==8]+=f[i-1][k][w][0][d4][d8];
f[i][j][0][1][d4||j==4][d8||j==8]+=f[i-1][k][w][1][d4][d8];
}
}
else
{

f[i][j][1][0][d4||j==4][d8||j==8]+=f[i-1][k][0][0][d4][d8];
f[i][j][1][1][d4||j==4][d8||j==8]+=f[i-1][k][0][1][d4][d8];
f[i][j][2][1][d4||j==4][d8||j==8]+=f[i-1][k][1][0][d4][d8];
f[i][j][2][1][d4||j==4][d8||j==8]+=f[i-1][k][1][1][d4][d8];
f[i][j][2][1][d4||j==4][d8||j==8]+=f[i-1][k][2][1][d4][d8];
}
read(L); read(R);
printf("%lld\n",Calc(R+1)-Calc(L));
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: