Time Limit: 2000MS | Memory Limit: 65536K | |
Total Submissions: 16036 | Accepted: 8159 |
Description
Step1. Connect the father's name and the mother's name, to a new string S.
Step2. Find a proper prefix-suffix string of S (which is not only the prefix, but also the suffix of S).
Example: Father='ala', Mother='la', we have S = 'ala'+'la' = 'alala'. Potential prefix-suffix strings of S are {'a', 'ala', 'alala'}. Given the string S, could you help the little cat to write a program to calculate the length of possible prefix-suffix strings of S? (He might thank you by giving your baby a name:)
Input
Restrictions: Only lowercase letters may appear in the input. 1 <= Length of S <= 400000.
Output
Sample Input
ababcababababcabab aaaaa
Sample Output
2 4 9 18 1 2 3 4 5
此题意思是让输出字符串中所有具有相同前后缀时的字符串长度。
已知 next数组中存放的是当前字符之前的字符串中具有相同前后缀的长度,
例如:next[i]=5;表示从字符串开始到下标为 i-1时,具有长度为5的相同前后缀子串
字符串:ababcababababcabab
1、长度为 18 时,字符串为 ababcababababcabab,前缀 ababcabab,后缀 ababcabab,输出18;
2、长度为 9 时,字符串为 ababcabab,前缀 abab,后缀abab,输出 9;
3、长度为 4 时,字符串为 abab,前缀 ab,后缀 ab,输出 4;
4、长度为 2 时,字符串为 ab,前缀 a,后缀 b,此时前后缀不相同,输出此时的字符串长度 2,并结束;
(因为字符串是从后向前一一查找判断的,所以当找到不想同的前后缀时既查找完毕,输出并结束)
......
如果还不明白,我就仍然以上述例子说,next[18]=9;意思是说,此字符串有长度为 9 的相同前后缀, 如上 1 所示,
设字符串长度为 9,此时next[9]=4,表示在此长度为 9 的前缀中,又有长度为 4 的相同的前后缀,
设字符串长度为 4,此时next[4]=2;.............
依次进行....
具体代码:
#include <stdio.h>
#include <string.h>
char s[400005];
int next[400005];
int ans[400005];
void Make_next(int len)
{
int i=0,j=-1;
memset(next,0,sizeof(next));
next[0]=-1;
while(i<len)
{
if(j==-1 || s[i]==s[j])
{
i++; j++;
next[i]=j;
}
else
j=next[j];
}
}
int main()
{
while(scanf("%s",&s)!=EOF)
{
int len=strlen(s);
Make_next(len);
int i,j=0;
memset(ans,0,sizeof(ans));
for(i=len;next[i]!=-1;)//直到找到没有前缀后缀相同为止
{
ans[j++]=i;//记录具有相同前后缀时的字符串的长度
i=next[i];
}
for(i=j-1;i>=0;i--)
printf("%d ",ans[i]);
printf("\n");
}
return 0;
}