poj2752 Seek the Name, Seek the Fame--------KMP

Seek the Name, Seek the Fame

Time Limit:2000MS

Memory Limit:65536K

Total Submissions:8143

Accepted:3822

Description

The little cat is so famous, that many couples tramp over hill and dale to Byteland, and asked the little cat to give names to their newly-born babies. They seek the name, and at the same time seek the fame. In order to escape from such boring job, the innovative little cat works out an easy but fantastic algorithm:

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

The input contains a number of test cases. Each test case occupies a single line that contains the string S described above.

Restrictions: Only lowercase letters may appear in the input. 1 <= Length of S <= 400000.

Output

For each test case, output a single line with integer numbers in increasing order, denoting the possible length of the new baby’s name.

Sample Input

ababcababababcabab

aaaaa

Sample Output

2 4 9 18

1 2 3 4 5

 

这题是找一个字符串的所有前缀和后缀相等的子串,只要充分理解了next函数的性质,那么这题就不难了。

现在举abcabcabc来说明,首先是构造next数组

 

下标

0

1

2

3

4

5

6

7

8

9

S

a

b

c

a

b

c

a

b

c

next

-1

0

0

0

1

2

3

4

5

6

len=9

在下标9处匹配失败,9是肯定符合要求的,回跳到下标6处,也就说明S的前6位是和后6位是一样的,6符合要求。下标6处匹配失败,回跳到下标3,说明3符合要求。从3跳到0,剩余的不再有符合要求的结果。于是将结果倒序输出即为3 6 9

 

#include<iostream>
#include<cstdlib>
#include<stdio.h>
#include<string.h>
#include<algorithm>
using namespace std;
const int maxm = 400010;     // 模式串的最大长度
char p[maxm];
int  m, next[maxm];
int d[maxm];
void getNext()
{
		int i = 0, j = next[0] = -1;
		while(i < m)
		{
			if (j == -1 || p[i] == p[j])
			{

				++i; ++j;
				next[i] = j;

			}
			else
            j = next[j];
		}

}

int main()
{
      while(scanf("%s",p)!=EOF)
      {
          m=strlen(p);
          getNext();
          int cc=0;
          for(int i=m;next[i]!=-1;i=next[i])
              d[cc++]=i;
          printf("%d",d[cc-1]);
          for(int i=cc-2;i>=0;i--)
          printf(" %d",d[i]);
          printf("\n");

      }
}

 

 

    原文作者:KMP算法
    原文地址: https://blog.csdn.net/qiqijianglu/article/details/7851229
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞