LA3026 KMP 关于循环节的问题
来源:互联网 发布:内控风险控制矩阵 编辑:程序博客网 时间:2024/05/19 23:56
题意:询问字符串前i个字符是否有循环节,求最小循环节的个数。
KMP的next函数有很多作用:
1.next[i]表示一个串与模式串的i位置的字符如果匹配不成功,下一个匹配的位置。
2.j=next[i]表示字符串中第i个字符与第j个字符相同(这里下标从1开始计算)
3.j=next[i]表示前j个字符与后j个字符相同,即0-(j-1)与(i-j+1)-(i)相同。
这题可以用到i-next[i]这个错位的部分。因为如果前i个字符是有循环节的话,那么i-next[i]一定是一个循环节,并且是最小的单元。为什么这里是最小的,因为如果有更大的,假设i-next[i]是next[i]的两倍,那么就与next()函数的定义有矛盾了,因为next()记录的是最大的前缀与后缀相同,而这里可以存在更大的前缀,即next[i]的两倍。
代码:
#include<iostream>#include<cstdio>#include<vector>#include<string>#include<queue>#include<cmath>#include<algorithm>#include<cstring>#define lson l,m,rt<<1#define rson m+1,r,rt<<1|1#define maxn 1000005#define INF 0xfffffff#define mem(a,b) memset(a,b,sizeof(a))#define FOR(i,s,t) for(int i=s;i<=t;i++)#define ull unsigned long long#define ll long longusing namespace std;char b[maxn];int next[maxn];int m;void getnext(){ int i=0,j=-1; next[i]=j; while(i<m) { while(j>=0&&b[i]!=b[j]) j=next[j]; i++;j++; next[i]=j; }}int main(){ int tt=1; while(scanf("%d",&m)==1) { if(!m) break; scanf("%s",b); getnext(); printf("Test case #%d\n",tt++); for(int i=2;i<=m;i++) { if(next[i]<=0) continue; if(i%(i-next[i])==0) { printf("%d %d\n",i,i/(i-next[i])); } } printf("\n"); }return 0;}
- LA3026 KMP 关于循环节的问题
- KMP LA3026
- LA3026||poj1961(KMP)
- LA3026 - Period(KMP)
- LA3026 Period [KMP]
- LA3026 KMP算法简单使用
- KMP求循环节问题
- (LA3026) Period -- KMP again (KMP 模板)
- KMP算法next数组的循环节问题
- poj 1961 KMP运用之循环节的问题
- KMP算法-next数组的应用-循环节问题
- la3026
- [KMP-循环节问题]HDU 1358 period
- HDU1358 Period KMP循环节问题
- 循环节的长度,循环节,循环次数(kmp)
- kmp最小循环节的求法
- 用kmp查找字符串的循环节
- 关于串的kmp匹配问题
- volatile(二)
- 初学者asp.net学习教程之进步流程
- android_Component之自定义组合控件
- (转)基于H.264的远程视频监控
- ASP.NET生成静态HTML源码示例(C#)
- LA3026 KMP 关于循环节的问题
- 最简单的ASP.NET数据库操作示例源代码
- Autoencoders
- ios socket编程初步:iphone客户端与java服务端通信
- Linux系统下获取帮助
- Trie 集合
- ASP.NET生成静态HTML页面的方法
- x86函数调用堆栈的操作
- struts2续