POJ 2406 Power Strings

Power Strings
Time Limit: 3000MS   Memory Limit: 65536K
Total Submissions: 39274   Accepted: 16309

Description

Given two strings a and b we define a*b to be their concatenation. For example, if a = "abc" and b = "def" then a*b = "abcdef". If we think of concatenation as multiplication, exponentiation by a non-negative integer is defined in the normal way: a^0 = "" (the empty string) and a^(n+1) = a*(a^n).

Input

Each test case is a line of input representing s, a string of printable characters. The length of s will be at least 1 and will not exceed 1 million characters. A line containing a period follows the last test case.

Output

For each s you should print the largest n such that s = a^n for some string a.

Sample Input

abcd
aaaa
ababab
.

Sample Output

1
4
3

Hint

This problem has huge input, use scanf instead of cin to avoid time limit exceed.

题意是给定一个字符串,如果把n个相同的字符串A连接在一起视为A^n的话,求给定的字符串的最大的n。

这个题目在看的时候没有看到最后是以.结束。。。WA了一次想了好久。

用KMP非常好求,字符串长度len减去next[len]就可以得到一个循环子串的长度。如果是len的因子的话,那么就可以输出字符串长度与这个循环子串的长度作为差,如果最后发现next[len]为len话,那么分别是只有一个字符,输出len就可以。其他情况就是没有循环子串,直接输出1就好。

代码如下:

/*************************************************************************
	> File Name: Power_Strings.cpp
	> Author: Zhanghaoran
	> Mail: chilumanxi@xiyoulinux.org
	> Created Time: Thu 26 Nov 2015 04:37:26 PM CST
 ************************************************************************/

#include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdio>
#include <cstdlib>

using namespace std;


void prekmp(char x[], int m, int nextKmp[]){
    int i = 0;
    int j = -1;
    nextKmp[0] = -1;
    while(i < m){
        if(j == -1 || x[i] == x[j])
            nextKmp[++ i] = ++ j;
        else 
            j = nextKmp[j];
    }
}

int nexti[1000010];
char a[1000010];

int main(void){
    while(~scanf("%s", a)){
        if(!strcmp(a, "."))
            break;
        int len =  strlen(a);
        prekmp(a, len, nexti);
        if((len % (len - nexti[len])) == 0)
            cout << len / (len - nexti[len]) << endl;
        else if(len - nexti[len] == 0)
            cout << len << endl;
        else 
            cout << "1" << endl;
        //for(int i = 0; i <= len;i ++)
        //    cout << nexti[i] << " ";
        //cout << endl;
    }
}


posted @ 2015-11-26 17:59  ChiLuManXi  阅读(163)  评论(0编辑  收藏  举报