KMP匹配算法,
网路上最简单最易懂的解释(虽然有错误)。
尊重原创...
地址:
http://www.ruanyifeng.com/blog/2013/05/Knuth%E2%80%93Morris%E2%80%93Pratt_algorithm.html
阮一峰老师的kmp算法逻辑有误,在
中有对该逻辑错误的解释。
该博客并没有代码实现,故实现如下:
使用js代码,按“F12”将代码扔入控制台便可运行。
1.获得next数组
function getNext(s) {
var next = [0];
var p1, p2;
var max = 0;
for (var i = 1; i < s.length; ++i) {
for (var j = 1; j <= i; ++j) {
p1 = s.substr(0, j);
p2 = s.substr(i - j + 1, j);
console.log(i + "::" + p1 + "==" + p2);
if (p1 == p2) {
max = max < p1.length ? p1.length : max;
}
}
next.push(max);
max = 0;
}
return next;
}
2.匹配字符串
有了next数组,接下来就是最简单的朴素模式匹配了,重点在于要根据next数组动态改变i值:
function kmp(s1, s2) {
var next = getNext(s2);
for (var i = 0; i < s1.length;) {
for (var j = 0; j < s2.length; j++) {
if (s1.charAt(i + j) != s2.charAt(j)) {
//重点:i +=(已匹配字符数 - 对应的部分匹配值),朴素模式匹配中,该处总为 i++;
//注意:在外层for循环中,并没有i++;
i += j > 0 ? (j - next[j - 1]) : 1;
j = next[j > 0 ? j-1 : 0];
break;
} else if (j == s2.length - 1) {
return i;
}
}
}
return -1;
}
运行结果(忽略next方法的输出):