http://acm.hdu.edu.cn/showproblem.php?pid=1686
Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
#include<cstdio> #include<cstring> #include<iostream> using namespace std; int n,len1,len2,f[1000001],ans; char s1[1000001],s2[1000001]; void getnext() { for(int i=1;i<len1;i++) { int j=f[i]; while(j&&s1[i]!=s1[j]) j=f[j]; f[i+1]= s1[i]==s1[j] ? j+1 : 0; } } void getans() { int j=0; for(int i=0;i<len2;i++) { while(j&&s1[j]!=s2[i]) j=f[j]; if(s1[j]==s2[i]) j++; if(j==len1) ans++; } printf("%d\n",ans); } int main() { scanf("%d",&n); while(n--) { cin>>s1>>s2; len1=strlen(s1);len2=strlen(s2); memset(f,0,sizeof(f)); getnext(); getans(); ans=0; } }
//由于字符串位置从0开始存 //所以f[i]在数值上=最大前缀子串=i的最大后缀子串=下一个要检验的位置 //也就是保证了 0——f[i]-1是相等的,再匹配i与f[i] #include<cstdio> #include<cstring> #include<iostream> using namespace std; int n,len1,len2,f[1000001],ans; char s1[1000001],s2[1000001]; void getnext() { for(int i=1;i<len1;i++)//注意这里从1开始 { int j=f[i];//j=下一个要匹配的位置 while(j&&s1[i]!=s1[j]) j=f[j]; f[i+1]= s1[i]==s1[j] ? j+1 : 0;//j+1:字符串从0开始,所以长度+1 } } void getans() { int j=0; for(int i=0;i<len2;i++)//这里从1开始 { while(j&&s1[j]!=s2[i]) j=f[j]; if(s1[j]==s2[i]) j++; if(j==len1) ans++; } printf("%d\n",ans); } int main() { scanf("%d",&n); while(n--) { cin>>s1>>s2; len1=strlen(s1);len2=strlen(s2); memset(f,0,sizeof(f)); getnext(); getans(); ans=0; } }
原文:http://www.cnblogs.com/TheRoadToTheGold/p/6483062.html