KMP 算法
给两个字符串,问 B 串是否是 A 串的子串。
假如,A="abababaababacb",B="ababacb"。两个指针 i 和 j 表示,A[i-
j+ 1..i]与 B[1..j]完全相等。就是说,i 不断增加,j 随着 i 变化,现在检验
A[i+1]和 B[j+1]。当 A[i+1]=B[j+1],i 和 j 各加一;当 j=m,则 B 是 A 的
子串,还能知道匹配位置。当 A[i+1]<>B[j+1],就减小 j 使 A[i-
j+1..i]=B[1..j]。
当 i=j=5:
i = 1 2 3 4 5 6 7 8 9 ……
A = a b a b a b a a b a b …
B = a b a b a c b
j = 1 2 3 4 5 6 7
A[6]<>B[6]。j 不能等于 5 了,要改成比它小的值 j'。j'当然越大越好。B
[1..5]="ababa",头 3 个字母和末 3 个字母都是"aba"。j’为 3 时,
A[6]=B[4]。于是,i 变成 6,j 变成 4:
i = 1 2 3 4 5 6 7 8 9 ……
A = a b a b a b a a b a b …
B = a b a b a c b
j = 1 2 3 4 5 6 7
从这个例子可以看到,j’取值与 i 无关,只与 B 串有关。可以预处理出数组
P[j],表示 B 数组第 j+1 个字母不能匹配时,j’最大值。P[j]是所有满足
B[1..P[j]]=B[j-P[j]+1..j]的最大值。
然后,A[7]=B[5],i 和 j 各加 1。这时又出现了 A[i+1]<>B[j+1]的情况:
i = 1 2 3 4 5 6 7 8 9 ……
A = a b a b a b a a b a b …
B = a b a b a c b
j = 1 2 3 4 5 6 7
由于 P[5]=3,因此 j’=3:
i = 1 2 3 4 5 6 7 8 9 ……
A = a b a b a b a a b a b …
B = a b a b a c b
j = 1 2 3 4 5 6 7
但 j’=3 仍不满足 A[i+1]=B[j+1],则再次减小 j’,将 j’再次更新为 P[3]:
i = 1 2 3 4 5 6 7 8 9 ……
A = a b a b a b a a b a b …
评论0