Cyclic Nacklace(HDU-3746)(KMP循环节)

来源:互联网 发布:mac spss 24破解dmg 编辑:程序博客网 时间:2024/05/21 18:45

Cyclic Nacklace

Problem Description
CC always becomes very depressed at the end of this month, he has checked his credit card yesterday, without any surprise, there are only 99.9 yuan left. he is too distressed and thinking about how to tide over the last days. Being inspired by the entrepreneurial spirit of "HDU CakeMan", he wants to sell some little things to make money. Of course, this is not an easy task.

As Christmas is around the corner, Boys are busy in choosing christmas presents to send to their girlfriends. It is believed that chain bracelet is a good choice. However, Things are not always so simple, as is known to everyone, girl's fond of the colorful decoration to make bracelet appears vivid and lively, meanwhile they want to display their mature side as college students. after CC understands the girls demands, he intends to sell the chain bracelet called CharmBracelet. The CharmBracelet is made up with colorful pearls to show girls' lively, and the most important thing is that it must be connected by a cyclic chain which means the color of pearls are cyclic connected from the left to right. And the cyclic count must be more than one. If you connect the leftmost pearl and the rightmost pearl of such chain, you can make a CharmBracelet. Just like the pictrue below, this CharmBracelet's cycle is 9 and its cyclic count is 2:

Now CC has brought in some ordinary bracelet chains, he wants to buy minimum number of pearls to make CharmBracelets so that he can save more money. but when remaking the bracelet, he can only add color pearls to the left end and right end of the chain, that is to say, adding to the middle is forbidden.
CC is satisfied with his ideas and ask you for help.
 
Input
The first line of the input is a single integer T ( 0 < T <= 100 ) which means the number of test cases.
Each test case contains only one line describe the original ordinary chain to be remade. Each character in the string stands for one pearl and there are 26 kinds of pearls being described by 'a' ~'z' characters. The length of the string Len: ( 3 <= Len <= 100000 ).
 
Output
For each case, you are required to output the minimum count of pearls added to make a CharmBracelet.

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


题目大意:

给你一个长度大于等于3的字符串,要求将字符串的全部字符最少循环2次需要添加的字符数。

例子:

abcabc 已经循环2次,添加数为0

abcac 没有循环2次,添加字符abcac。数目为5.

abcabcab 已经循环过2次,但第三次不完整,需要添加数为1


题目分析:

对KMP循环节的一个应用。跟以前写的那个POJ-2406不太一样,这道题还需要求出需要添加多少。

但是公式上次已经给出了:

KMP最小循环节、循环周期:

定理:假设S的长度为len,则S存在最小循环节,循环节的长度L为len-next[len],子串为S[0…len-next[len]-1]。

(1)如果len可以被len - next[len]整除,则表明字符串S可以完全由循环节循环组成,循环周期T=len/L。

(2)如果不能,说明还需要再添加几个字母才能补全。需要补的个数是循环个数L-len%L=L-(len-L)%L=L-next[len]%L,L=len-next[len]。

这个证明在这里:  ------------------------->KMP最小循环节讲解


代码:

#include <iostream>#include <algorithm>#include <cstdio>#include <cstring>#include <cmath>#include <queue>#include <vector>using namespace std;typedef long long LL;const int N=100000+999;char s2[N];int nex[N];void makeNext(int n){    int i,j;    nex[0] = 0;    for (i = 1,j = 0; i < n; i++)    {        while(j > 0 && s2[i] != s2[j])            j = nex[j-1];        if (s2[i] == s2[j])            j++;        nex[i] = j;    }}int main(){    int n,t;    scanf("%d",&t);    while(t--)    {        scanf(" %s",s2);        n=strlen(s2);        memset(nex,0,sizeof(nex));        makeNext(n);        int j=nex[n-1];//1到n-1的前缀后缀最大匹配长度        int x=n-j;     //最小循环节长度        if(n%x==0&&n!=x) //能否组成循环,特判 n==x的时候会出现abcd的情况并不能组成            printf("0\n");        else        {            printf("%d\n",x-n%x);//还缺少几个字符构成循环节        }    }    return 0;}





 



原创粉丝点击