- KMP匹配模式算法
每当一趟匹配过程中出现字符比较不等时,不需要回溯I指针,而是利用已经的带的“部分匹配”的结果将模式向右滑动尽可能远的一段距离后,继续进行比较。
即尽量利用已经部分匹配的结果信息,尽量让i不要回溯,加快模式串的滑动速度。
Pk=Pj next[j+1]=next[j]+1
Pk≠Pj next[j+1]=next[k]+1
已知next[0~6],求next[7、8]
next[7]: ∵next[6]=3,P6≠P3,next[3]=1
∴比较P6、P1(P6≠P1),next[1]=0
∴next[7]=0+1=1
next[8]: ∵next[7]=1,P7=P1
∴next[8]=1+1=2
KMP匹配模式算法实现代码
//串的KMP匹配模式算法
//ch1_6
#include<stdio.h>
#include<stdlib.h>
#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0
#define MAXSTRLEN 100
typedef char SString[MAXSTRLEN + 1];
//子串求next[n]算法
void get_next(SString t, int next[]) {
next[1] = 0;//第一个next为0
int j = 1, k = 0;
while (j < t[0]) {//小于串长
if (k == 0 || t[j] == t[k]) {
++j, ++k;
next[j] = k;
}
else
k = next[k];
}
}
//KMP算法
int KMPindex(SString s, SString t, int pos) {
if (pos<1 || pos>s[0])
return ERROR;
int i = pos, j = 1;
int next[MAXSTRLEN];
get_next(s, next);//求next[]
while (i <= s[0] && j <= t[0]) {//都小于串长
if (j==0||s[i] == t[j]) {
//j==0,此条件必须加
i++, j++;
}
else
j = next[j];
}
if (j > t[0])
return i - t[0];
return ERROR;
}
int main() {
SString a = { 6,'a','b','a','d','a','b' };
SString b = { 2,'a','b' };
for (int i = 1; i <= a[0]; i++)
printf("%c ", a[i]);
printf("\n");
for (int i = 1; i <= b[0]; i++)
printf("%c ", b[i]);
printf("\n");
int pos1 = KMPindex(a, b, 1);
int pos2 = KMPindex(a, b, 2);
printf("%d %d\n", pos1, pos2);
return 0;
}