c语言主范式与编码,超详细!终于搞明白KMP算法
小伙伴们好久不见,今天将开设“数据结构与算法”专栏,一起梳理一遍硬核课程的重要知识点,那我们开始吧
正文
「字符串匹配」是计算机的基本任务之一,举个栗子,有一个字符串“「aaaaaaca」",我想知道里面是否包含另一个字符串“「aaaac」”,该怎么办?
这里就会使用到「串的模式匹配算法」,最常见的分别是传统的「Brute-Force(暴力)算法」和「KMP算法」。
BF算法设计思想
1、主串和模式串逐个字符进行比较
2、当出现「字符串不相同」时,也就是「失配」时,主串的比较位置重置为起始位置的下一个字符位置,模式串的比较位置重置为起始位置
3、匹配成功后返回主串中匹配串的起始位置,否则就返回错误代码
BF算法的设计缺陷及解决方案
在BF算法中,每次失配都需要回溯指向上次比较起始字符的下一个字符。通过观察发现:在回溯的时候,已匹配似乎「有一部分」没必要继续比较了,这样可以降低算法的「时间复杂度」
「KMP」算法的出现有效地解决了BF算法的缺陷。KMP 算法是 D.E.Knuth、J,H,Morris 和 V.R.Pratt 三位神人共同提出的。
但是这种算法相对于BF算法不太容易理解,网上也有很多解释,但配图有点少,总感觉差点意思,下面我通过画图的方式详细介绍KMP算法的设计思想和工作原理
KMP算法设计思想
在匹配过程中出现字符比较不相等时,「主串 S」已比较的位置不回溯,「模式串 T」比较的位置进行移动
在匹配过程中有一个难题需要解决:如何计算「模式串 T」失配时的移动位数?经过三位牛人的研究,设计出了「部分匹配函数」
部分匹配函数
部分匹配函数是KMP算法中最难以理解的部分。首先需要理解「前缀」、「后缀」、「最大共有长度」的概念。
· 前缀:指除了最后一个字符以外,一个字符串的全部头部组合
· 后缀:指除了第一个字符以外,一个字符串的全部尾部组合
· 最大共有长度(部分匹配值):指前缀和后缀中的最大共有元素,没有则为0。例如“abab”的前缀为“a”、“ab”、“aba”,后缀为“b”、“ab”、“bab”,最大共有元素为“ab”,所以最大共有长度为 2
回顾一下KMP算法的匹配过程:
红线框出的部分恰好就是失配时已匹配部分,“aaaa” 的最大共有元素为 “aaa”,这一部分字符就是不需要再重复进行比较直接跳过的字符
在代码实现过程中,j 移动后的位置 = 模式串 T 的起始位置下标 + 部分匹配值。通常起始下标为 0,因此 j 移动后位置 = 部分匹配值,即 j = next[j],next[j] 就是「部分匹配函数」,j 为失配时的位置
因此接下来就成了对部分匹配函数的是实现。将 “aaaac” 以首字符起始的所有子串的最大共有长度枚举出来,构成「部分匹配表」,它描述了失配时的下标 j 与部分匹配值的关系
部分匹配表则是通过模式串 T 的自匹配实现:
示例代码(C语言哦):
/*KMP匹配算法*/
int KMPCompare(HString parent, HString child, intpos) {
int next[255];
Get_Next(child, next);
int i = pos - 1;
int j = 0; //j用于子串child中的起始位置
while (i
if (j == 0 || parent.ch[i] == child.ch[j]) {
++i;
++j;
}
else {
j = next[j]; //i不变,j后退
}
}
if (j == child.length) {
return (i + 1) - j;
}
return 0;
}
/*部分匹配函数的实现*/
void Get_Next(HString child, int * next) {
int i = 0;
int j = -1;
next[0] = -1; //不会用到
while (i
if (j == -1 || child.ch[i] == child.ch[j]) {
++i;
++j;
next[i] = j;
}
else {
j = next[j];
}
}
}
void main() {
/*使用KMP算法匹配串*/
HString parent, child;
StrAssign_HeapString(&parent, "BBC ABCDAB ABCDABCDABDE");
StrAssign_HeapString(&child, "ABCDABD");
printf("Index = %d\n", KMPCompare(parent, child, 1));
}
复制代码
关注即可提高学习效率!我是Aime菌,下期再见!Peace~
每天进步一点点,慢一点才能走得更快
c语言主范式与编码,超详细!终于搞明白KMP算法相关推荐
- c语言有关字符的操作,C语言字符操作总结大全(超详细).doc
C语言字符串操作总结大全(超详细) 作者: 本篇文章是对C语言字符串操作进行了详细的总结分析,需要的朋友参考下 1)字符串操作 strcpy(p, p1) 复制字符串 strncpy(p, p1, n ...
- 一年半´力扣´练习生超详细总结(附数据结构+算法)
一年半´力扣´练习生超详细总结(附数据结构+算法) 文章目录 一年半´力扣´练习生超详细总结(附数据结构+算法) 我与力扣 数据结构 算法 未来计划 其他专栏推荐 我与力扣 专栏导航:LeetCode ...
- C语言基础入门笔记(超详细笔记,多出进行更新,将近九千字)
下载VS2013,我们一起学习. #include 包含一个叫stdio.h的文件,文件包含令,预处理指令. stdio.h C语言的标准I/O库,用于读取和写入文件,也用于控制台的输入和输出. ma ...
- c++ 字符串连接_C语言字符串操作总结大全(超详细)
本篇文章是对C语言字符串操作进行了详细的总结分析,需要的朋友参考下 1)字符串操作 strcpy(p, p1) 复制字符串 strncpy(p, p1, n) 复制指定长度字符串 strcat(p, ...
- C语言文件操作函数总结——超详细
版权声明 本文原创作者:谷哥的小弟 作者博客地址:http://blog.csdn.net/lfdfhl 文件与流 在C语言中有三种标准流: stdin(standard input stream)标 ...
- Mac上安装R语言运行环境及RStudio [超详细!~]
前言 我们需要安装:1)R语言环境,2)Rstudio软件(R语言开发工具). 我的安装方法参考了博文mac上安装R和RStudio,感谢作者. 接下来分步骤展示详细方法,并给出一个运行示例~ Ste ...
- 【C语言初级阶段学习1】使用vscode运行C语言,vscode配置环境超详细过程(包括安装vscode和MinGW-W64安装及后续配置使用的详细过程,vscode用户代码片段的使用)[考研专用]
vscode配置c语言环境 前言 一.下载vscode和MinGW-W64和安装过程 1. vscode部分 1.1 vscode下载安装过程 1.2 vscode下载插件 2. MinGW-W64部 ...
- c语言1066字符分类统计,C语言字符串操作总结大全(超详细)
1)字符串操作strcpy(p, p1) 复制字符串 strncpy(p, p1, n) 复制指定长度字符串 strcat(p, p1) 附加字符串 strncat(p, p1, n) 附加指定长度字 ...
- C语言字符串操作总结大全(超详细)
1)字符串操作 strcpy(p, p1) 复制字符串 strncpy(p, p1, n) 复制指定长度字符串 strcat(p, p1) 附加字符串 strncat(p, p1, n) 附加指定长度 ...
最新文章
- 换掉VMware?轻量级虚拟机,横空出世!
- 比特币要升级成为“比特币现金”
- 重构第15天 移除重复的代码(Remove Duplication)
- 【转】grep搜索子目录中包含某字符串的特定文件
- 关于fflush、缓冲区、scanf、EOF等问题真麻烦
- Apache Kafka-通过concurrency实现并发消费
- Ubuntu环境使用conda安装轻量级中文ocr开源项目chineseocr_lite,最简单的方式
- Windows系统进程介绍
- JavaScript反向shell
- hdu2844 amp; poj1742 Coin ---多重背包--两种方法
- 成都东软学院大学生计算机基础excel作业,成都东软学院
- Matlab R2016a安装教程
- WPF介绍和一些基础操作
- cc2500的register操作
- BT5 U盘制作方法
- DTMF信号检测分析(Matlab)
- 关于一台电脑安装多个jdk后使用时如何切换
- 个人技术博客的选择:CSDN、博客园、简书、知乎专栏、Github、新浪、个人建站等?
- cesium城市建筑颜色渲染以及泛光渐变效果
- bzoj3926 诸神眷顾的幻想乡 后缀自动机
热门文章
- VTK修炼之道74:交互部件_Widget的创建
- 从用户接触到完成需求说明书
- linux-IO之copy的实现
- android.content.Context.getResources()‘ on a null object reference
- 如何用Linux写c程序并编译运行
- sort函数——利用函数实现快速排序c++
- 程序员面试系列——插入排序
- 8086处理器的无条件转移指令——《x86汇编语言:从实模式到保护模式》读书笔记13
- Object的finalize方法
- 汽车车牌识别系统(六)-- 项目中的各个文件解析