FZU 1901 KMP找前后缀等串

来源:互联网 发布:江南大学网络教育登陆 编辑:程序博客网 时间:2024/06/17 13:40


Period II
Time Limit:1000MS     Memory Limit:32768KB     64bit IO Format:%I64d & %I64u
 FZU 1901

Description

For each prefix with length P of a given string S,if

S[i]=S[i+P] for i in [0..SIZE(S)-p-1],

then the prefix is a “period” of S. We want to all the periodic prefixs.

Input

Input contains multiple cases.

The first line contains an integer T representing the number of cases. Then following T cases.

Each test case contains a string S (1 <= SIZE(S) <= 1000000),represents the title.S consists of lowercase ,uppercase letter.

Output

For each test case, first output one line containing "Case #x: y", where x is the case number (starting from 1) and y is the number of periodic prefixs.Then output the lengths of the periodic prefixs in ascending order.

Sample Input

4oooacmacmacmacmacmafzufzufzufstostootssto

Sample Output

Case #1: 31 2 3Case #2: 63 6 9 12 15 16Case #3: 43 6 9 10Case #4: 29 12

#include <iostream>#include <cstdio>#include <algorithm>#include <string>using namespace std;int nex[1000005];int k;int ans[1000005];void pre(string str){    nex[0]=-1;    int i=0,j=-1;    while(i<str.size()){        if(j==-1||str[i]==str[j]){            j++;i++;            nex[i]=j;        }else            j=nex[j];    }}void kmp(string str){    pre(str);    int len=str.size();    int i=len-1;    k=0;    while(i>-1){        if(str[i]==str[len-1]) ans[k++]=len-i-1;        i=nex[i];    }}int main(){    std::cout.sync_with_stdio(false);    string str;    int n;    while(cin>>n){        for(int t=1;t<=n;t++){            cin>>str;            kmp(str);            cout<<"Case #"<<t<<": "<<k<<endl;            for(int i=1;i<k;i++)                cout<<ans[i]<<' ';            cout<<str.size()<<endl;        }    }}



0 0