数据结构字符串匹配KMP算法的详解(题目讲解 简单易懂)

简介: 数据结构字符串匹配KMP算法的详解(题目讲解 简单易懂)

有问题欢迎评论区私信留言交流~~~

博主近来在复习数据结构的过程中遇到了KMP字符串匹配算法,在浏览了网上众多文章后感觉写的不够清晰和简单易懂,尤其是从做题的角度上来讲,下面就个人对KMP算法的理解进行解题,有问题还请谅解~

首先我们来看一下KMP算法的定义

KMP算法定义

KMP算法是一种改进的字符串匹配算法,由D.E.Knuth,J.H.Morris和V.R.Pratt提出的,因此人们称它为克努特—莫里斯—普拉特操作(简称KMP算法)。KMP算法的核心是利用匹配失败后的信息,尽量减少模式串与主串的匹配次数以达到快速匹配的目的。具体实现就是通过一个next()函数实现,函数本身包含了模式串的局部匹配信息。KMP算法的时间复杂度O(m+n)

KMP算法是三位学者在 Brute-Force算法的基础上同时提出的模式匹配的改进算法。Brute- Force算法在模式串中有多个字符和主串中的若干个连续字符比较都相等,但最后一个字符比较不相等时,主串的比较位置需要回退。KMP算法在上述情况下,主串位置不需要回退,从而可以大大提高效率

所以我们可以明确KMP算法的核心就是当一位字符串匹配失败后子串应该移动的距离,所以关键是要求出这个移动的距离,明确了我们的目标之后下面我们以具体的题目进行讲解

基本概念

首先我们明确几个题目中要用到的基本概念

1:主串 就是要被匹配的串

2:字串 也称模式串,用于匹配主串

3:前缀

4:后缀

5:最长相等前后缀长度

6:部分匹配值PM

7:next数组

8:nextval数组

想必大家看到上面如此多的概念难免头晕犯难,下面我们以具体的题目进行讲解,这个算法实际上非常好理解

前缀指的是除最后一个字符外,字符串的所有头部字串。后缀指的是除第一个字符外,字符串的所有尾部子串,部分匹配值即为字符串的前缀和后缀的最长相等前后缀长度

下面我们从一个具体的例子来求解以上概念

按照规则一个个求前后缀即可,这里有一个小坑就是后缀是从往前的,所以是ba bab...

那么上面的部分匹配值表中某个字符不匹配时子串需要向后移动的位数计算公式如下

移动位数=已匹配的字符数-对应字符的部分匹配值

切记,此处查找的是最后一个匹配字符即下图b的部分匹配值

方法如下图所示,其余字符不匹配方法相同,直至字符串匹配成功或匹配失败为止

这里写错了 应该是b的部分匹配值为0

那么问题来了,既然上面已经可以计算出移动位数,那么next和nextval数组又是什么呢?

因为上面的计算方法还是不够直观和简单,还要查找上一个字符的部分匹配值,所以我们进一步简化,将PM表整体右移一位,就得到了next数组,第一个元素右移后空缺用-1填充,最后一个元素右移溢出不用理会直接舍去,有时为了计算方便也可以next数组值整体加1,这点应根据题目干条件灵活应对,其实串为序从1开始就整体+1,从0开始则不用加

此时移动位数=已匹配字符数-对应部分的next数组值(即不用看上一位的部分匹配值)

所以上图中的next数组为-1 0 0 01 如果加1则为 0 1 1 1 2读者可自行验证

最后nextval数组就是对KMP算法的进一步优化,失配时如果Pj=Pnext[j]则会匹配相等的字符,解决办法是递归计算next[j]并将更新后的next[j]命名为nextval[j],递归计算方法为

nextval[j]=next[next[j]]

如果递归一次后仍然相等则继续递归,直至不等即可

创作不易 觉得有帮助请点赞关注收藏~~~

相关文章
|
2月前
|
存储 C语言
栈和队列题目练习
栈和队列题目练习
19 0
|
2月前
|
算法
第四章 KMP算法理论基础
第四章 KMP算法理论基础
19 0
|
2月前
|
算法
KMP算法
KMP算法
34 0
|
4月前
|
算法 C++
A : DS串应用–KMP算法
这篇文章提供了KMP算法的C++实现,包括计算模式串的next数组和在主串中查找模式串位置的函数,用于演示KMP算法的基本应用。
|
4月前
|
算法 Java
LeetCode经典算法题:矩阵中省份数量经典题目+三角形最大周长java多种解法详解
LeetCode经典算法题:矩阵中省份数量经典题目+三角形最大周长java多种解法详解
52 6
|
4月前
|
算法
KMP算法
KMP算法
31 0
|
5月前
|
算法 Java
KMP算法详解及其在字符串匹配中的应用
KMP算法详解及其在字符串匹配中的应用
|
2月前
|
算法 安全 数据安全/隐私保护
基于game-based算法的动态频谱访问matlab仿真
本算法展示了在认知无线电网络中,通过游戏理论优化动态频谱访问,提高频谱利用率和物理层安全性。程序运行效果包括负载因子、传输功率、信噪比对用户效用和保密率的影响分析。软件版本:Matlab 2022a。完整代码包含详细中文注释和操作视频。
|
13天前
|
算法 数据安全/隐私保护 索引
OFDM系统PAPR算法的MATLAB仿真,对比SLM,PTS以及CAF,对比不同傅里叶变换长度
本项目展示了在MATLAB 2022a环境下,通过选择映射(SLM)与相位截断星座图(PTS)技术有效降低OFDM系统中PAPR的算法实现。包括无水印的算法运行效果预览、核心程序及详尽的中文注释,附带操作步骤视频,适合研究与教学使用。