mark一下,重新温习了 KMP
KMP复杂度O(n+m)
这里有一个解释的超级的好的博客,大家可以去看一下:http://blog.csdn.net/v_july_v/article/details/7041827
换言之,对于给定的模式串:ABCDABD,它的最大长度表及next 数组分别如下:
根据最大长度表求出了next 数组后,从而有
失配时,模式串向右移动的位数为:失配字符所在位置 - 失配字符对应的next 值
void GetNext(char* p,int next[]) { int pLen = strlen(p); next[0] = -1; int k = -1; int j = 0; while (j < pLen ) { //p[k]表示前缀,p[j]表示后缀 if (k == -1 || p[j] == p[k]) { ++k; ++j; next[j] = k; } else { k = next[k]; } } }
-
int KmpSearch(char* s, char* p) { int i = 0; int j = 0; int sLen = strlen(s); int pLen = strlen(p); while (i < sLen && j < pLen) { //①如果j = -1,或者当前字符匹配成功(即S[i] == P[j]),都令i++,j++ if (j == -1 || s[i] == p[j]) { i++; j++; } else { //②如果j != -1,且当前字符匹配失败(即S[i] != P[j]),则令 i 不变,j = next[j] //next[j]即为j所对应的next值 j = next[j]; } } if (j == pLen) return i - j; else return -1; }
hdu 1711模板题
#include<cstdio> #include<cstring> #include<iostream> using namespace std; int n,m; int a[1000005]; //匹配串 int b[1000005]; //模式串 int next[1000005]; void get_next(){ next[0]=-1; int k=-1; int j=0; while(j<m){ //b[k]表示前缀,b[j]表示后缀 if(k==-1 || b[j]==b[k]){ ++k; ++j; next[j]=k; } else{ k=next[k]; } } } int kmp(){ int i=0,j=0; while(i<n&&j<m){ //①如果j = -1,或者当前字符匹配成功(即a[i] == b[j]),都令i++,j++ if(j==-1||a[i]==b[j]){ i++; j++; } else{ j=next[j]; } } if(j==m) return i-j+1; else return -1; } int main(){ int i,t; scanf("%d",&t); while(t--){ scanf("%d%d",&n,&m); for(i=0;i<n;i++) scanf("%d",&a[i]); for(i=0;i<m;i++) scanf("%d",&b[i]); get_next(); int ans=kmp(); printf("%d\n",ans); } return 0; }
hdu 2203 同样是模板题
#include<stdio.h> #include<string.h> int n,m; char a[200005]; //匹配串 char b[200005]; //模式串 int next[200005]; void get_next(){ next[0]=-1; int k=-1; int j=0; while(j<m){ //b[k]表示前缀,b[j]表示后缀 if(k==-1 || b[j]==b[k]){ ++k; ++j; next[j]=k; } else{ k=next[k]; } } } int kmp(){ int i=0,j=0; while(i<n&&j<m){ //①如果j = -1,或者当前字符匹配成功(即a[i] == b[j]),都令i++,j++ if(j==-1||a[i]==b[j]){ i++; j++; } else{ j=next[j]; } } if(j==m) return i-j+1; else return -1; } int main(){ int i,t; while(gets(a)){ n=strlen(a); for(i=0;i<n;i++){ a[i+n]=a[i]; } n=2*n; gets(b); m=strlen(b); get_next(); int ans=kmp(); if(ans==-1){ printf("no\n"); } else{ printf("yes\n"); } } return 0; }
时间: 2024-11-05 12:19:34