算法介绍

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

next数组

  我们记主串为字符串S,模式串为字符串P。

  我们用next[j]表示以字符Pj结尾的子串的长度相等的前缀字符串与后缀字符串长度的最大值

  特别地,当没有满足条件的子串时,next[j] = 0。

  为了方便起见,我们将字符串从下标1开始匹配。如此,next数组所表示的长度就与下标数值相等了。

算法思路

  我们从左到右依次枚举S的每一个字符Si,对于当前待匹配字符Si,我们假设当前P字符串中已匹配到Pj。

  那么我们只需判断Si和Pj+1,若两者相同,则继续匹配。

  若两者不相同,那么我们使j=next[j],即可最大限度的减少匹配次数。因为S字符串的从某位置开始到前i-1的部分与P字符串的前j个字符已匹配(即完全相同),如图中两蓝色直线所夹的S、P的两段,而P1到Pnext[j]部分是长度最大的与以Pj结尾的后缀完全相同的前缀(图中绿色线段),而该以Pj结尾的后缀则必定与S中一段以Si-1结尾的子串完全相同,因而保证了上述操作的正确性。

  接下去只需重复上述操作即可。

  而对于next数组的预处理,也同上述操作类似,我们只需要以字符串P来匹配字符串P即可。

模板呈现

  模板题链接:KMP字符串

  代码如下:

#include <iostream>
#include <algorithm>
#include <cstdio>
using namespace std;
const int M = 1e5+;
int n,m;
int ne[M];
char s[M],p[M];
int main()
{
cin>>n>>p+;
cin>>m>>s+; for(int i=,j=;i<=n;i++)
{
while(j && p[i]!=p[j+])j=ne[j];
if(p[i]==p[j+])j++;
ne[i]=j;
}
for(int i=,j=;i<=m;i++)
{
while(j && s[i]!=p[j+])j=ne[j];
if(s[i]==p[j+])j++;
if(j==n)
{
printf("%d ",i-n+-);
j=ne[j]; //可有可无,好习惯要加上。若为string,不加会出错。
}
}
printf("\n");
return ;
}

数据结构——KMP算法的更多相关文章

  1. 数据结构--KMP算法总结

    数据结构—KMP KMP算法用于解决两个字符串匹配的问题,但更多的时候用到的是next数组的含义,用到next数组的时候,大多是题目跟前后缀有关的 . 首先介绍KMP算法:(假定next数组已经学会, ...

  2. 实验数据结构——KMP算法Test.ming

    翻译计划     小明初学者C++,它确定了四个算术.关系运算符.逻辑运算.颂值操作.输入输出.使用简单的选择和循环结构.但他的英语不是很好,记住太多的保留字,他利用汉语拼音的保留字,小屋C++,发明 ...

  3. 数据结构-kmp算法

    定义 改进字符串的匹配算法 关键:通过实现一个包含了模式串的局部匹配信息的next()函数,利用匹配失败的信息,减少匹配次数. 1.BF算法 暴力匹配 给定 文本串S "BBC ABCDAB ...

  4. <数据结构>KMP算法

    next数组 定义 严格定义:next[i]表示使子串s[0...k] == s[i-k...i]的最大的k(前后缀可以重叠,但不能是s[0..i]本身) 含义:最长相等前后缀的下标,没有则赋-1 图 ...

  5. 大话数据结构——KMP算法(还存在问题)

    http://www.ruanyifeng.com/blog/2013/05/Knuth%E2%80%93Morris%E2%80%93Pratt_algorithm.html /*#include& ...

  6. 数据结构KMP算法中手算next数组

    总结一下今天的收获(以王道数据结构书上的为例子,虽然我没看它上面的...):其中竖着的一列值是模式串前缀和后缀最长公共前缀. 最后求得的结果符合书上的结果,如果是以-1开头的话就不需要再加1,如果是以 ...

  7. 数据结构- 串的模式匹配算法:BF和 KMP算法

      数据结构- 串的模式匹配算法:BF和 KMP算法  Brute-Force算法的思想 1.BF(Brute-Force)算法 Brute-Force算法的基本思想是: 1) 从目标串s 的第一个字 ...

  8. 数据结构与算法--KMP算法查找子字符串

    数据结构与算法--KMP算法查找子字符串 部分内容和图片来自这三篇文章: 这篇文章.这篇文章.还有这篇他们写得非常棒.结合他们的解释和自己的理解,完成了本文. 上一节介绍了暴力法查找子字符串,同时也发 ...

  9. 【数据结构】KMP算法

    我还是不太懂... 转2篇大神的解释    1>https://www.cnblogs.com/yjiyjige/p/3263858.html     2>https://blog.csd ...

随机推荐

  1. NEST指定id

    1.默认以Id属性为Id,无Id属性则自动生成 2.可通过属性标签指定Id [ElasticsearchType(IdProperty = nameof(last_name))] public cla ...

  2. eigenface算法笔记

    昨天看了PCA(PCA算法介绍见上一篇),今天继续看eigenface,在这里把eigenface的过程梳理下: EigenFace本质上讲,是把人脸从像素空间变换到另一个空间,在另一个空间中做相似性 ...

  3. ElementUI动态表格数据转换formatter

    elementUI的表格初始化比较简单,声明prop值对应的字段名即可. 而在实际应用中,我们常常有这种需求:从服务器获取的数据并不是我们要显示的最终结果,涉及一些状态.类型.日期时间等的转换,这时候 ...

  4. iOS应用开发---返回到指定界面

    关于ios中 viewcontroller的跳转问题,其中有一种方式是采用navigationController pushViewController 的方法,比如我从主页面跳转到了一级页面,又从一 ...

  5. JAVA笔记整理(二),下载安装JDK

    Windows平台 1.登录Oracle官方网站(http://www.oracle.com/index.html),找到下载 2.选择要下载的版本,点击JDK DOWNLOAD 3.下载文件,先勾选 ...

  6. seo域名选择

    1-1第一选域名: 1,简单好记,有意义. 2,后缀首选com 其次cn 1-2购买域名网站有 1,阿里云 2,godaddy 3 ,景安 购买是可以在这三个域名平台都看看价格有些不一样.(可以省钱) ...

  7. Gitlab CI/CD任务一直处于pending

    在注册Runner时候这里输入了tag,这里指的是runner的标签,可以设置多个  ,分别用 ,号分割 .gitlab-ci.yml文件中 stages: - pull - package - bu ...

  8. 软硬RAID 和 不常见的RAID

    若转载请于明显处标明出处:http://www.cnblogs.com/kelamoyujuzhen/p/5561809.html 为啥子引入RAID? 存储最现实的两个问题:速度.容量 001——计 ...

  9. Linux常用命令【1】

    打包和压缩文件 : cd /home 进入 '/ home' 目录' cd .. 返回上一级目录 cd ../.. 返回上两级目录 cd 进入个人的主目录 cd ~user1 进入个人的主目录 cd ...

  10. 关于zsh-autosuggestions插件导致粘贴内容很慢的问题

    zsh开启autosuggestions 插件的时候,在终端中粘贴大量的内容的时候,会粘贴的很慢,基本上是一个字符一个字符的粘贴的. 解决方案 在.zshrc文件中配置以下内容: # This spe ...