[BZOJ1511][POI2006]OKR-Periods of Words(kmp+dp)

来源:互联网 发布:廉价机票 知乎 编辑:程序博客网 时间:2024/04/29 08:08

题目描述

传送门

题解

题目要求求除了其本身的最长循环节,实际上就是要求非0的最短失配。
但是如果直接求最短失配的话,应该在求出最长失配的基础上暴力向前蹦,这样的话时间承受不了。那么可以转化一下思路,最长循环节是有递推关系的,即f(i)+=f(T(i))+(i-T(i)),T为失配函数。这样的话时间就可以做到O(n)了。

代码

#include<iostream>#include<cstring>#include<cstdio>using namespace std;#define N 1000005#define LL long longint n,T[N];char s[N];LL f[N],ans;void calc_T(){    T[0]=-1;    for (int i=0;i<n;++i)    {        int j=T[i];        while (j!=-1&&s[i]!=s[j])            j=T[j];        T[i+1]=++j;    }}int main(){    scanf("%d\n",&n);    gets(s);    calc_T();    for (int i=1;i<=n;++i)        if (T[i])        {            f[i]+=f[T[i]]+((LL)i-(LL)T[i]);            ans+=f[i];        }    printf("%lld\n",ans);}

总结

①kmp的失配可以与dp(还有树结构)联系起来!这一点以后要注意!

0 0
原创粉丝点击