[luogu4127 AHOI2009] 同類分佈 (數位dp)
阿新 • • 發佈:2018-11-09
Solution
裸數位dp,空間存不下只能列舉數字具體是什麼
注意memset最好為-1,不要是0,有很多狀態答案為0
Code
//By Menteur_Hxy #include <cmath> #include <cstdio> #include <cstdlib> #include <cstring> #include <iostream> #include <algorithm> #define Re register #define Fo(i,a,b) for(Re int i=(a),_=(b);i<=_;i++) #define Ro(i,a,b) for(Re int i=(b),_=(a);i>=_;i--) #define getchar() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin)),p1==p2?EOF:*p1++) using namespace std; typedef long long LL; char buf[1<<21],*p1,*p2; inline LL read() { LL x=0,f=1;char c=getchar(); while(!isdigit(c)) {if(c=='-')f=-f;c=getchar();} while(isdigit(c)) x=(x<<1)+(x<<3)+(c^48),c=getchar(); return x*f; } LL MOD; LL dp[20][200][200],bit[20]; LL dfs(LL pos,LL sum,LL mod,LL lim) { if(!pos) return (sum==MOD&&mod==0); if(!lim&&~dp[pos][sum][mod]) return dp[pos][sum][mod]; int up=lim?bit[pos]:9; LL res=0; Fo(i,0,up) res+=dfs(pos-1,sum+i,(mod*10+i)%MOD,lim&&i==bit[pos]); if(!lim) dp[pos][sum][mod]=res; return res; } LL sol(LL x) { LL len=0,res=0; while(x) bit[++len]=x%10,x/=10; for(MOD=1;MOD<=len*9;MOD++) { memset(dp,-1,sizeof(dp)); res+=dfs(len,0,0,1); } return res; } int main() { LL l=read(),r=read(); printf("%lld",sol(r)-sol(l-1)); return 0; }