1. 程式人生 > >bzoj 3530 [Sdoi2014]數數

bzoj 3530 [Sdoi2014]數數

ctime soft name lld play tin closed names lin

傳送門

de了整整三個小時bug.

一直擔心我的數位dp,然而並沒錯。

AC自動機各種毛病,fail怎麽都不對,DE到懷疑人生,

最後發現我tmd用了一個棧來get_fail;

一直用stl突然心血來潮要手寫一個隊列,結果我tmd寫成了一個棧。。

今晚真的是懷疑人生,

技術分享圖片
//Achen
#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<vector>
#include<queue>
#include
<cmath> #include<ctime> const int N=1507; const int mod=1e9+7; typedef long long LL; using namespace std; int m,lim[N],s[N]; LL dp[N][N][3],ans; void read(int a[]) { char ch=getchar(); while(ch<0||ch>9) ch=getchar(); for(;ch>=0&&ch<=9;ch=getchar()) a[++a[0
]]=ch-0; } int rt,tot,ch[N][10],is[N],fail[N]; void insert() { int x=rt; for(int i=1;i<=s[0];i++) { int c=s[i]; if(!ch[x][c]) ch[x][c]=++tot; x=ch[x][c]; } is[x]=1; } queue<int>que; void get_fail() { que.push(rt); while(!que.empty()) {
int x=que.front(); que.pop(); for(int i=0;i<10;i++) if(ch[x][i]) { int y=ch[x][i]; if(x==rt) fail[y]=rt; else { int z=fail[x]; for(;!ch[z][i]&&z;z=fail[z]); if(ch[z][i]) fail[y]=ch[z][i]; else fail[y]=rt; if(is[fail[y]]) is[y]=1; } que.push(ch[x][i]); } } } void pls(LL &a,LL b) { a+=b; if(a>=mod) a-=mod;} void solve() { dp[0][0][1]=1; dp[0][0][2]=1; for(int i=1;i<=lim[0];i++) for(int j=0;j<=tot;j++) if(!is[j]&&(dp[i-1][j][0]||dp[i-1][j][1]||dp[i-1][j][2])) { for(int k=(i==1);k<10;k++) { int y=ch[j][k]; if(!y) { int tp=fail[j]; while(!ch[tp][k]&&tp) tp=fail[tp]; if(ch[tp][k]) y=ch[tp][k]; else y=rt; } if(is[y]) continue; if(i==3&&y==0) { int cnm=0; } pls(dp[i][y][2],dp[i-1][j][2]); pls(dp[i][y][0],dp[i-1][j][0]); if(k<lim[i]) pls(dp[i][y][0],dp[i-1][j][1]); if(k==lim[i]) pls(dp[i][y][1],dp[i-1][j][1]); } } for(int i=1;i<=lim[0];i++) { int debug=1; for(int j=0;j<=tot;j++) if(!is[j]) { if(i<lim[0]) pls(ans,dp[i][j][2]); else { pls(ans,dp[i][j][0]); pls(ans,dp[i][j][1]); } } } } int main() { read(lim); cin>>m; for(int i=1;i<=m;i++) { s[0]=0; read(s); insert(); } get_fail(); solve(); printf("%lld\n",ans); return 0; } /* 7391 3 21 1923 98 */
View Code

bzoj 3530 [Sdoi2014]數數