http://acm.hdu.edu.cn/showproblem.php?pid=2594
这里有一点要注意,前缀必须要从头开始算,后缀要从最后一个数开始算,中间截一段相同字符串是不行的。
再回到next[i]的定义,对于串ptr = "ababaaababaa";
next[0] = -1,代表着除了第一个元素,之前前缀后缀最长的重复子串,这里是空 ,即"",没有,我们记为-1,代表空。(0代表1位相同,1代表两位相同,依次累加)。
next[1] = 0,即“a”,没有前缀与后缀,故最长重复的子串是空,值为-1;
next[2] = 0,即“ab”,前缀是“a”,后缀是“b”,最长重复的子串“”;
next[3] = 1,即"aba",前缀是“ab”,后缀是“ba”,最长重复的子串“a”;next数组里面就是最长重复子串字符串的个数
next[4] = 2,即"abab",前缀是“aba”,后缀是“bab”,最长重复的子串“ab”;
next[5] = 3,即"ababa",前缀是“abab”,后缀是“baba”,最长重复的子串“aba”;
next[6] = 1,即"ababaa",前缀是“ababa”,后缀是“babaa”,最长重复的子串“a”;
next[7] = 1,即"ababaaa",前缀是“ababaa”,后缀是“babaaa”,最长重复的子串“a”;
next[8] = 2,即"ababaaab",前缀是“ababaaa”,后缀是“babaaab”,最长重复的子串“ab”;
next[9] = 3,即"ababaaaba",前缀是“ababaaab”,后缀是“babaaaba”,最长重复的子串“aba”;
next[10] = 4,即"ababaaabab",前缀是“ababaaaba”,后缀是“babaaabab”,最长重复的子串“abab”;
next[11] = 5,即"ababaaababa",前缀是“ababaaabab”,后缀是“babaaaababa”,最长重复的子串“ababa”;
#include<bits/stdc++.h> using namespace std; const int maxn=600010; char s1[maxn*2],s2[maxn]; int nxt[maxn*2]; void getnext(char *a) { int i=-1,j=0; int len=strlen(a); nxt[0]=-1; while(j<len) { if(i==-1||a[i]==a[j]) { j++; i++; nxt[j]=i; } else i=nxt[i]; } } int main() { while(cin>>s1>>s2) { int lena=strlen(s1),lenb=strlen(s2),len=lena+lenb; strcat(s1,s2); getnext(s1); // for(int i=0;i<=len;i++) //cout<<nxt[i]<<" "; while(nxt[len]>lena||nxt[len]>lenb) //例如 ababb aababba 合起来ababbaababba next[11]=6; //next[6]=1 len=nxt[len]; len=nxt[len]; for(int i=0; i<len; ++i)cout<<s1[i]; if(len)cout<<' '; cout<<len<<endl; } return 0; }