2025dsfz-KMP学习笔记
Upd 2025-07-30: 补充注释和文字内容
前言:这把高端局
关于KMP
- 时间复杂度为 的优秀字符串查找算法。
- 适用于在句子/文章中查找一段文字(词语)。
KMP实现
关于共同前后缀数组(PMT)
-
说人话就是 数组。
-
是什么?
- 表示下标从 到 的子串(后文中叫做 串)中既是 的前缀串又是 的后缀串的字符串的最长长度。
- 举例说明:开始时候的串为:
abcab- 那 ,因为存在串 既是 的前缀又是 的后缀,而且在所有满足条件的串中,它是最长的。所以把 设为它的长度—— .
-
构建 的详细步骤
- 初始化:设模式串为 ,长度为 ,创建一个长度为 的数组 来存储部分匹配表(相当于 数组)的值。初始化 ,因为模式串的第一个字符的前缀子串只有一个字符,不存在相等的前后缀。
- 遍历模式串:从模式串的第二个字符开始遍历,即 到 。对于每个位置 ,设两个指针,一个指针 j 指向当前前缀子串的最长相等前后缀的下一个位置,初始时 。
-比较字符:比较 和 。如果 等于 ,说明找到了更长的相等前后缀,此时 ,然后将 后移一位,即 ,继续下一个位置的比较。 - 不相等情况:如果 不等于 ,且 ,则将 更新为 ,继续比较 和 。这是因为当 和 不相等时,需要回溯到 位置之前的最长相等前后缀的下一个位置,继续进行比较。
- 最终结果:当遍历完整个模式串后, 数组中存储的就是模式串的部分匹配表。
-
示例
- 以模式串
“ababaca”为例: - 首先初始化 。
- 对于 ,即字符
“b”,其前缀子串“a”不存在相等前后缀,所以 。 - 对于 ,字符
“a”,前缀子串“ab”也不存在相等前后缀,。 - 对于 ,字符
“b”,此时前缀子串“aba”,发现前缀“a”和后缀“a”相等,所以 。 - 对于 ,字符
“a”,前缀子串“abab”,最长相等前后缀为“ab”,所以 。 - 对于 ,字符
“c”,先看 ,比较“c”和“b”不相等,再将 更新为 ,此时“c”和“a”也不相等,所以 。 - 对于 ,字符
“a”,先看 ,比较“a”和“a”相等,所以 。 - 最终得到的 PMT 数组为
[0, 0, 0, 1, 2, 0, 1]。
- 对于 ,即字符
- 以模式串
-
数组生成代码
-
如果没明白随便用这组数据模拟一遍 数组的生成过程:
ABACABAB
1 |
|
查找
- 如果当前字符匹配,那就继续进行,否则就把首个模式串的位置设置为当前位置的 数组对应的值的下标。(咕咕咕)
1 |
|
问题 A: 【一本通提高篇KMP】剪花布条 P3375 【模板】KMP
解法
- 就是板子
1 |
|
P4391 [BalticOI 2009]【一本通提高篇KMP】Radio Transmission(BZOJ1355)
解法
就是利用next数组的离奇关系来解决.
1 |
|
本博客所有文章除特别声明外,均采用 GNU GPL 3.0 许可协议。转载请注明来源 FrankWkd!

