KMP算法简单总结

数据结果 kmp算法实验报告 kmp算法,数据结构的实验报告,大学实验报告,希望能帮到大家 立即下载

kmp算法根据我自己的理解就是,kmp算法就是来判断两个字符串存不存在包含关系。也就是一个主字符串a,副字符串b,判断字符串a中是否有子串,以及有多少子串或者子串的位置,等等这些问题。

总体思想就是主串和子串进行匹配时,子串到你匹配失败的那一个点之前的几个位置是否有与开头的字符一样,如果有就返回开头与匹配结尾失败的地方样位置的下一个,如果不一样就移动到首位。

我理解的KMP算法的思想就是先构造next数组,通过next来是实现减少时间复杂度,那么next数组如何构造呢。先附一张图

就是先对子串进行匹配,什么叫做对子串进行匹配就是看看子串中是否有重的,子串从一个字符开始,然后两个。。。。。用next来存子串中重复重复出现的位置,图中的数字是前i个字符的意思。子串对于然后就是对子串和主串同时操作了,如果主串和子串中第一个不匹配,子串一直保持在首位不会移动,主串的字符不断移动,当子串和主串匹配时,主串和子串一起移动,直到遇不匹配的时候,子串会再次移动到主串的位置,主串接着往下移动,如果子串和主串匹配成功的时候,如果还想接着匹配主串接着移动,子串就重新回到首位,接着上述操作进行匹配。举个例子:

 

Oulipo

链接:http://acm.hdu.edu.cn/showproblem.php?pid=1686

该题就用KMP算法来找主串中子串出现的次数

​
#include<stdio.h>
#include<iostream>
#include<string.h>
using namespace std;
#define N 10005
string a, b;
int next[N];
int sum;
void Getnext(string a){//进行构造next数组
     int i = 0, j = -1;
     next[0] = -1;
     int len = a.size();
     while(i < len){
        while(j != -1 && a[i] != a[j])j = next[j];//如果没有一样的就返回首位,否则就子串中i和j向下移动一个位置
     i++;
     j++;
     next[i] = j;
     }

}
void KMP(string a, string b){
    int n = a.size(), m =  b.size();
    int i = 0, j = 0;
    Getnext(b);
    while(i < n){
        while(j != -1 && a[i] != b[j])j = next[j];//如果没有一样的就返回首位,否则就子串和主串向下移动一个位置
        i++;
        j++;
        if(j >= m){//当匹配成功的时候返回首位
            sum ++;
            j = next[j];
        }
    }


}
int main(){
    int T;
    cin>>T;
    string a, b;
    while(T--){
        cin>>a>>b;
        sum = 0;
        KMP(b,a);
        cout<<sum<<endl;
    }
return 0;
}

​

                                      入侵检测

链接:http://acm.hrbust.edu.cn/index.php?m=ProblemSet&a=showProblem&problem_id=1309

本题就是利用KMP算法查找主串中是否含有子串

#include<stdio.h>
#include<iostream>
#include<string.h>
using namespace std;
#define N 10005
string a, b;
int ne[N];
int sum;
void Getnext(string a){//进行构造next数组
     int i = 0, j = -1;
     ne[0] = -1;
     int len = a.size();
     while(i < len){
        while(j != -1 && a[i] != a[j])j = ne[j];//如果没有一样的就返回首位,否则就子串中i和j向下移动一个位置
     i++;
     j++;
     ne[i] = j;
     }

}
int KMP(string a, string b){
    int n = a.size(), m =  b.size();
    int i = 0, j = 0;
    Getnext(b);
    int flag = 0;
    while(i < n){
        while(j != -1 && a[i] != b[j])j = ne[j];//如果没有一样的就返回首位,否则就子串和主串向下移动一个位置
        i++;
        j++;
        if(j == m)//当匹配成功的时候返回首位
        {
            flag = 1;
        }
     }

    if(flag )return i - j;
    else return -1;


}
int main(){
    string a, b;
    while(cin>>a>>b){
        cout<<KMP(a, b)<<endl;
        if(KMP(a, b) == 1)cout<<"yes"<<endl;
        else cout<<"no"<<endl;

    }
return 0;
}
 

下面的代码就是对上面的进行补充,就是返回第一个找到的位置。

#include<stdio.h>
#include<iostream>
#include<string.h>
using namespace std;
#define N 10005
string a, b;
int ne[N];
int sum;
void Getnext(string a){//进行构造next数组
     int i = 0, j = -1;
     ne[0] = -1;
     int len = a.size();
     while(i < len){
        while(j != -1 && a[i] != a[j])j = ne[j];//如果没有一样的就返回首位,否则就子串中i和j向下移动一个位置
     i++;
     j++;
     ne[i] = j;
     }

}
int KMP(string a, string b){
    int n = a.size(), m =  b.size();
    int i = 0, j = 0;
    Getnext(b);
    int flag = 0;
    while(i < n){
        while(j != -1 && a[i] != b[j])j = ne[j];//如果没有一样的就返回首位,否则就子串和主串向下移动一个位置
        i++;
        j++;
        if(j == m)//如果匹配成果就break掉,做一个标记,
        {
            flag = 1;
            break;
        }
     }

    if(flag )return i - m;//当检测有这个标记的时候证明,已经匹配成功
    else return -1;


}
int main(){
    string a, b;
    while(cin>>a>>b){
        cout<<KMP(a, b)<<endl;
    }
return 0;
}

 

 

 

数据结构课程设计实验报告-KMP算法的实现 KMP算法是对一般模式匹配算法的改进,由D.E.Knuth与V.R.Pratt和J.H.Morris 同时发现的因此人们称它为克努特-莫里斯-莫拉特操作(简称为KMP算法)。 对于一般的模式匹配算法:分别利用两个指针i和j指示主串S和T中的当前正待比较的字符位置。算法的基本思想是:从主串的S的第POS个字符开始起和模式的第一个字符比较之,如相等,则继续逐个比较后续字符;否则从主串的下一个字符起再重新和模式的字符比较之。以此类推,直到模式T中的每个字符依次和主串S中的一个连续字符序列相等,则称匹配成功,则函数值为和模式T中的第一个字符相等的字符在主串S中的序号,否则称匹配不成功,函数值为0.而对于模式匹配的KMP算法可以在O(n+m)的时间数量级上完成串的模式匹配操作。其改进过程在于:每当一趟匹配过程出现字符比较不相等时,不需回溯i指针,而是利用已经得到的部分匹配的结果将模式串向右滑动一段尽可能远的距离后,继续进行比较。滑动的这一段距离我们将会用到函数Next[], KMP算法的最大特点是指示主串的指针不须回溯,整个匹配过程中,对主串仅需从头到尾扫描一遍,这对处理从外设输入的庞大文件很有效,可以边度入边匹配,而无需回头重读。 开发工具:C语言 立即下载

相关推荐

stm32驱动NRF24L01_原理+代码解析

NRF24L01是NORDIC公司生产的一款无线通信通信芯片,采用FSK 调制,集成NORDIC自家的Enhanced Short Burst协议。可以实现点对点或是1对6的无线通信。无线通信速度最高可达到2Mbps。①2.4G全球开放的ISM频段,免许可证使用。②最高工作速率2Mbps,高校的GFSK调制,抗干扰能力强。③126个可选的频道,满足多点通信和调频通信的需要。④内置CRC检错和点对多点的通信地址控制。⑤可设置自动应答,确保数据可靠传输。//NRF24L01寄存器操作命令。

zyc18700766982的博客 2万+

KMP算法总结

KMP算法(一)(对比暴力匹配算法) KMP算法(研究总结,字符串) KMP算法的作用是在A串中查找是否有B串的算法,时间复杂度为O(n+m)。原理是利用上次匹配的信息,这次匹配并不是从上一次A串中开始匹配的下一个位置开始,而是直接从上一次匹配的不匹配位置开始,且不是从头匹配B串,而是匹配B串中还未匹

qq_46514141的博客 1061

centos7下100T存储扩容(LVM)至150T

查看新增磁盘情况lsblk,fdisk -l [root@localhost ~]# lsblk NAME MAJ:MIN RM SIZE RO TYPE MOUNTPOINT sr0 11:0 1 4.2G 0 rom vda 252:0 0 80G 0 disk ├─vda1 252:1 0 1G 0 part /boot └─vda2 252:2

tiyager的博客 1024

《数据结构》实验报告四:串的模式匹配(BF算法、KMP算法)

《数据结构》实验报告:串的模式匹配 - BF算法、KMP算法实现 + 目标串nextval数组算法实现

Amentos的博客 1万+

Python | 处理CMIP6 NC数据,以tas为例

各位同学,一般在文章最后一章我们可能会做不同气候情景下变量的未来时空变化特征,类似上图。从cmip6下载的nc数据常需要转换格式、裁剪到研究区和重采样等,本期代码可以解决这类问题。

qq_48539301的博客 1384

Sharding Sphere JDBC使用Mybatis的saveBatch无法返回主键的问题

Sharding Sphere JDBC使用Mybatis的saveBatch无法返回主键的问题

HHCS231的博客 1829

KMP算法总结笔记

首先我们思考,在上述问题中,如果求解过程中,人为去求解的话,肯定不会这样一次一次的直接返回去对比,而是在T[i]!=P[j]时,首先会直接跳过前面已匹配过的字符串,例如:对比面对上述不匹配的情况时,暴力解法 《》我们现在想要直接进行的跳转的区别是,i并未动,直接把j移动到了0,这是我们需要去思考一个问题,眼睛可以直接看到,我们可以这样去移动,但是代码如何去设计呢?这个规律是如何找到的?

itbird的专栏 569

【go-libp2p学习笔记】使用go-libp2p搭建中转服务器(circuit relay server)

libp2p算是一个蛮新的库,提供了非常强大的p2p节点发现/连接/通信能力。IPFS的基石。 中文网上的**技术教程**比较少,所以抛砖引玉开一点坑来体验一下!

Cake_C的博客 6490

kmp算法总结

kmp算法,是一种减少字符串匹配时复杂度的算法,本算法减少了两个字符串遇到不相等的情况是的匹配次数,也就是减少了主串的回溯次数,跳过了不必要的匹配,使原来的m*n的时间复杂度变成了m+n。 Kmp算法大致分为两个部分: 1:next数组 next数组,next数组记录了模式串前缀后缀的长度,求模式串的next数组是使用kmp算法的前提,也是根本,next数组的求法:首先定义一个函数,将所求模...

yewenhu的博客 360

飞牛fnNAS搭建个人小账本

本文介绍了如何在飞牛NAS上部署ezBookkeeping个人记账应用。该开源工具支持多平台使用,具备双因素认证、多级分类等功能。文章详细讲解了Docker激活、镜像下载、容器部署等步骤,并展示了账户管理、交易记录等基础操作。同时指导用户通过ZeroTier实现远程访问,方便随时随地使用个人记账系统。该方案既保障了数据隐私,又提供了专业记账功能,适合对财务隐私敏感的用户。

dgnankai的专栏 781

基于YOLOv11的手写数字与符号识别系统设计与实现

手写数字与符号识别系统需要丰富多样的训练数据才能达到理想的泛化性能。MNIST:包含70,000个手写数字样本(0-9),28x28灰度图像优点:干净整齐,适合初学者缺点:多样性不足,只有数字EMNIST:MNIST的扩展,包含数字、字母(大小写)和特殊符号样本量:814,255张图像覆盖62个类别(10数字+26小写字母+26大写字母)HASYv2:专门的手写符号数据集包含369个不同符号类别约168,000个标注实例包括数学符号、箭头、括号等:英文手写文本数据库。

YOLO 290

KMP算法总结(二)

说完了KMP算法的一些基本的操作,我们再来说一下KMP算法的代码实现: 写代码的时候和上面我们所说的操作都是一样的: 首先我们需要完成的就是prefix-table的构建,为了大家能更好的理解,我们使用一串新的字符串作为例子进行讲解: 我们写出它所有的前缀和最长公共前后缀的长度为: 我们从中可以发现一个规律: 例如:我们拿字符串:“A B A B C A”和字符...

JoJoJo1234的博客 612

【数据集5】土地利用类型数量预测数据LUH2

简介土地利用类型数量预测数据LUH2

WW、forever的博客 4546

KMP算法真的很简单1

spark 11.9999 Normal 0 7.8 pt 0 2 false false false MicrosoftInternetExplorer4

sparkliang的专栏 1万+

win10 跳过U8环境检测的IE WebControls.rar

win10 安装u8的时候 提示IE WebControls 不通过,这个工具可以欺骗u8的检查。 跳过U8环境检测的IE WebControls。提示导入失败后,重新检测通过。

IDEA的使用指南

IDEA基于java的使用手册,可以最快速的上手,在使用中不断的丰富自己的使用技巧.

简单模式匹配算法和KMP算法

参见原文 简单模式匹配算法 经典的模式匹配,是让模式串的首字符从主串的首字符开始向右匹配。 匹配的规则是: 1.在主串的第i个位置,让pos=i,如果主串pos位置的字符等于模式串的第一个字符,则pos++,再与模式串的第二个字符进行匹配。 2.如果又相等则继续向下匹配,直到匹配到模式串的结尾,就说明主串中存在该模式串;如果不相等,则停止匹配,回到主串中,并i++。 3.然后再让pos=i,重复上述步骤,直到i到达主串结尾。 相应代码如下: #include<stdio.h> #include&

ccxcuixia 2371

SIMATIC S7-1200, S7-1500 PID 控制[手册]

SIMATIC S7-1200, S7-1500 PID 控制[手册]

简单模式匹配算法和KMP模式匹配算法

 KMP 字符串模式匹配详解 KMP字符串模式匹配通俗点说就是一种在一个字符串中定位另一个串的高效算法。简单匹配算法的时间复杂度为O(m*n);KMP匹配算法。可以证明它的时间复杂度为O(m+n).。一 . 简单匹配算法先来看一个简单匹配算法的函数:int Index_BF ( char S [ ], char T [ ], int pos ){/* 若串 S 中从第pos(S 的下标0≤p

u012934610的专栏 1738

VB摄像头监控

该VB模块可对摄像头捕获的画面进行录像等,可在创建的窗口进行控制

串的模式匹配算法(简单模式匹配、KMP、改进的KMP)

一、简单模式匹配 思想:从主串的第一个位置起和模式串的第一个字符进行匹配,如果相等则继续匹配,否则从主串的第二个字符开始逐一比较。以此类推,知道全部匹配完成。 如:str: ababc str1:abc 第一轮匹配:匹配失败,下次从str的第二个元素继续进行匹配 ababc abc 第二轮匹配:匹配失败,下次从str的第三个元素继续进行匹配 a...

hi_sir_destroy的博客 1961

【数据结构】串的简单模式匹配算法、KMP算法(C语言)

目录串的简单模式匹配算法简单模式匹配算法完整实现代码运行结果KMP算法 串的简单模式匹配算法 简单模式匹配 Brute-Force(布鲁斯-福斯)算法是一种带回溯的匹配算法,算法的基本思想是:从主串 s 的第一个字符开始,和模式串 t 的第一个字符开始比较,如果相等,就继续比较后续字符,如果不等,则回溯到主串 s 的第2个字符开始重新和模式串 t 比较,直到模式串 t 中的每一个字符和主串 s 中的一个连续字符子序列全部相等,则称匹配成功,返回和 t 中第一个字符相等的字符在主串 s 中的位置;或者主串中没

weixin_51450101的博客 5717

串的模式匹配算法:简单匹配算法、KMP模式匹配

串的模式匹配算法:简单匹配算法、KMP模式匹配 简单匹配算法 时间复杂度:O(n*m) int Index(Sstring S, int pos, Sstring T) { int i=pos, j=1; while(i<=S.len && j<=T.len) { if(S.ch[i]==T.ch[j]) { i++; j++; } else { i=i-j+2; j=1; } } if(j>=T.len) r

m2426675454的博客 344

KMP 算法真的很简单

KMP算法真的很简单<br />KMP是字符串匹配的经典算法,曾经一度对其敬而远之,感觉很难写出来正确的KMP算法,这都是拜那些“教科书”所赐,在它们的教授下,不禁感觉KMP很难!<br />其实理解KMP算法很简单,今天就来看个究竟,我的目标就是从几个简单的数学等式推导出KMP算法,简单但严谨。串匹配<br />先来回忆一下串匹配场景,不外乎是给定两个字符串S和T,然后在S串中查找T串,如果查找成功就是匹配,否则就是不匹配。比如:<br />S = “avantar-titanic”; T = “avan

Stoneson 674

数据结构-串的模式匹配算法(简单匹配、KMP)

模式匹配是数据结构中字符串的一种基本运算,给定一个子串,要求在某个字符串中找出与该子串相同的所有子串。假设P是给定的子串,T是待查找的字符串,要求从T中找出与P相同的所有子串,这个问题称为模式匹配问题。P称为模式,T称为目标。如果T中存在一个或多个模式为P的子串,就给出该子串在T中的位置,称为匹配成功;否则匹配失败。

2301_79704601的博客 717

KMP算法其实很简单

目录 KMP算法产生原因 前缀和后缀 next数组求解过程 KMP算法 KMP算法产生原因 朴素算法(BF)进行模式串匹配的思想为将模式串与主串进行字符比较,如果相等,那么模式串和主串中对应位置的指针均往后前进一步,如果模式串中所有的字符都匹配成功了,则表示主串中包含模式串,但如果在某一位置不等,则从主串的下一位置开始重新和模式串进行比较,如果指向主串的指针越界,咋表示匹配失败。BF算法其思想比较简单,实现过程也并不复杂,网上相关博客很多,这里不做赘述,如果读者不懂BF算法,可进行查阅分析。好了

FDk_LCL的博客 671

KMP算法的简单实现

一直把精力放在web应用的开发和框架学习,应用,架构的领悟等等这些几乎见不到算法存在的场景中,对算法这个‘内功’修炼一直有种没处下牙的尴尬境地。不过这不代表从此不再接触算法,一味的只去掌握JDK封装好的API库。今天使用String的indexOf(...)的时候突然想看看这个方法的实现,于是... 1.6.0.17的算法实现主要代码: [code="jav...

code dream 138

简单模式匹配算法的优化——KMP算法

KMP算法 让我们先看看简单模式匹配算法的代码 简单模式匹配算法 //方案① int Index(String S,String T){ int i,j; int k=1; while(i<=S.length&&j<=T.length){ if(S.ch[i]==T.ch[j]){ i++; j++ } else{ i=k; j=1; k++; } } if(j>T.length){ return k; }

#两个西柚 744

算法其实很简单—KMP算法

目录 1. KMP算法介绍 2. KMP算法最佳应用—字符串匹配问题 3. 思路 4. 代码实现 4.1 KMP算法实现 4.2 暴力匹配算法实现 1. KMP算法介绍 KMP是一个解决模式串在文本串是否出现过,如果出现过,最早出现的位置的经典算法 Knuth-Morris-Pratt字符串查找算法,简称为“KMP算法”,常用于在一个文本串S内查找一个模式串P的出现位置,这个算法由Donald Knuth、Vaughan Pratt、James H. Morris三人于1977年联合发表,

我愿随风而行 的博客 333
上一篇: BigInteger(简单了解)
下一篇: 求数组(连续)在某一区间最大值(简单的动态规划的思想)
Re:fused
博客等级 码龄9年 474粉丝 162原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值