Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 9588 Accepted Submission(s): 4480
代码:
//dp[i]表示字符串s[1~i]中出现了多少个以s[i]为结尾的前缀,又有f数组的特性,如果 //f[i]=j则s[1~j]=s[i-j+1~i]得出状态转移方程dp[i]=dp[f[i]]+1; #include<iostream> #include<cstdio> #include<cstring> using namespace std; const int mod=10007; char P[200005]; int f[200005],dp[200005]; int main() { int t,n; scanf("%d",&t); while(t--){ scanf("%d",&n); scanf("%s",P); f[0]=f[1]=0; for(int i=1;i<n;i++){ int j=f[i]; while(j&&P[i]!=P[j]) j=f[j]; f[i+1]=(P[i]==P[j]?j+1:0); } dp[0]=0; int sum=0; for(int i=1;i<=n;i++){ dp[i]=dp[f[i]]+1; sum+=dp[i]%mod; sum%=mod; } printf("%d\n",sum); } return 0; }
原文:http://www.cnblogs.com/--ZHIYUAN/p/6420647.html