KMP
1 // KMP
2
3 void get_next(char s[],int next[])
4 {
5 int i,j;
6 i=1;j=0;
7 next[1]=0;
8 int len=strlen(s);
9 while(i<len)
10 {
11 if(j==0||s[i-1]==s[j-1])
12 {
13 i++;
14 j++;
// next[i]=j; 求最大循环次数用这个,不用下面的优化
15 if(s[i-1]==s[j-1])
16 next[i]=next[j];
17 else
18 next[i]=j;
19 }
20 else
21 j=next[j];
22 }
23 }
24
25 void KMP(char *s,char *t,int pos)// 从s的第pos开始
26 {
get_next(t,next);
27 int i=pos;
28 int j=1;
29 int len1=strlen(s);
30 int len2=strlen(t);
31 while(i<=len1&&j<=len2)
32 {
33 if(j==0||s[i-1]==t[j-1])
34 {
35 i++;
36 j++;
37 }
38 else
39 j=next[j];
40 }
41 if(j>len2)
42 return i-len2-1;
43 else
44 return -1;
45 }
int m=len-next[len];
if(len%m==0&&t[len-1]==t[next[len]-1])
printf("%d\n",len/m);// 最大循环次数
else
printf("1\n");
if(t[len-1]==t[next[len]-1])
cout<<next[len]<<endl; //最大的前后公共缀的长度。
void output(int i) //从小到大输出所有的前后公共缀的长度
{
if(next[i]&&t[i-1]==t[next[i]-1])
{
output(next[i]);
printf("%d ",next[i]);
}
}
亲和串
Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 8818 Accepted Submission(s): 4013
Problem Description
人随着岁数的增长是越大越聪明还是越大越笨,这是一个值得全世界科学家思考的问题,同样的问题Eddy也一直在思考,因为他在很小的时候就知道亲和串如何
判断了,但是发现,现在长大了却不知道怎么去判断亲和串了,于是他只好又再一次来请教聪明且乐于助人的你来解决这个问题。
亲和串的定义是这样的:给定两个字符串s1和s2,如果能通过s1循环移位,使s2包含在s1中,那么我们就说s2 是s1的亲和串。
亲和串的定义是这样的:给定两个字符串s1和s2,如果能通过s1循环移位,使s2包含在s1中,那么我们就说s2 是s1的亲和串。
Input
本题有多组测试数据,每组数据的第一行包含输入字符串s1,第二行包含输入字符串s2,s1与s2的长度均小于100000。
Output
如果s2是s1的亲和串,则输出"yes",反之,输出"no"。每组测试的输出占一行。
Sample Input
AABCD
CDAA
ASD
ASDF
Sample Output
yes
no
1 #include <iostream> 2 #include <cstdio> 3 #include <cstring> 4 #include <cmath> 5 #include <algorithm> 6 #include <string> 7 #include <vector> 8 #include <stack> 9 #include <queue> 10 #include <set> 11 #include <map> 12 #include <iomanip> 13 using namespace std; 14 const int INF=0x5fffffff; 15 const int MS=200005; 16 const double EXP=1e-8; 17 char str1[MS],str2[MS/2]; 18 int next[MS/2]; 19 20 void get_next(char s[],int next[]) 21 { 22 int i,j; 23 i=1;j=0; 24 next[1]=0; 25 int len=strlen(s); 26 while(i<len) 27 { 28 if(j==0||s[i-1]==s[j-1]) 29 { 30 i++; 31 j++; 32 if(s[i-1]==s[j-1]) 33 next[i]=next[j]; 34 else 35 next[i]=j; 36 } 37 else 38 j=next[j]; 39 } 40 } 41 42 int KMP(char *s,char *t,int pos)// 从s的第pos开始 43 { 44 get_next(t,next); 45 int i=pos; 46 int j=1; 47 int len1=strlen(s); 48 int len2=strlen(t); 49 while(i<=len1&&j<=len2) 50 { 51 if(j==0||s[i-1]==t[j-1]) 52 { 53 i++; 54 j++; 55 } 56 else 57 j=next[j]; 58 } 59 if(j>len2) 60 return i-len2-1; 61 else 62 return -1; 63 } 64 65 66 67 int main() 68 { 69 while(scanf("%s%s",str1,str2)!=EOF) 70 { 71 sprintf(str1,"%s%s",str1,str1); 72 /* 73 if(strstr(str1,str2)!=NULL) 74 printf("yes\n"); 75 else 76 printf("no\n"); 77 */ 78 if(KMP(str1,str2,1)>=0) 79 printf("yes\n"); 80 else 81 printf("no\n"); 82 } 83 return 0; 84 }