HDU 3746 Cyclic Nacklace(KMP找循环节)

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2087

题目大意:给你一个字符串,求出将字符串的最少出现两次循环节需要添加的字符数。

解题思路:

这题需要利用next数组的性质,求出字符串的最小循环节

有几个结论(具体可以看这里http://www.cnblogs.com/wuyiqi/archive/2012/01/06/2314078.html):

①字符串长度为len,则len-next[len]为最小循环节。

②如果len%(len-next[len])==0,此字符串的最小周期就为len/(len-next[len])。

借用以上结论,我们可以直接判断字符串是否已满足条件,或者需要补齐的字符数。

 1 #include<iostream>
 2 #include<cstdio>
 3 #include<cstring>
 4 #include<algorithm>
 5 using namespace std;
 6 const int N=1e6+5;
 7 
 8 int len;
 9 int nxt[N];
10 char p[N];
11 
12 void getnext(){
13     int i,j;
14     i=0,j=nxt[0]=-1;
15     while(i<len){
16         while(j!=-1&&p[i]!=p[j])
17             j=nxt[j];
18         nxt[++i]=++j;
19     }
20 }
21 
22 int main(){
23     int t;
24     scanf("%d",&t);
25     while(t--){
26         scanf("%s",p);
27         len=strlen(p);
28         getnext();
29         int mmin=len-nxt[len];              //len-nxt[len]为字符串的最小循环节
30         if(len!=mmin&&len%mmin==0)          //含有两个以上循环节
31             puts("0");
32         else
33             printf("%d\n",mmin-len%mmin);   //len%mmin等同于"abcab"减掉"abc"
34     }
35     return 0;
36 }

 

posted @ 2018-03-01 00:13  Yeader  阅读(224)  评论(0编辑  收藏  举报