图解KMP以及next数组的求法
在计算机科学中,Knuth-Morris-Pratt字符串查找算法(简称为KMP算法)可在一个主文本字符串S内查找一个模式串P的出现位置。此算法通过运用对这个模式串在不匹配时本身就包含足够的信息来确定下一个匹配将在哪里开始的发现,从而避免重新检查先前匹配的字符。
今天写完kmp的题, 发现又想不通了, 这个next数组实在是太绕了, 去跑步的路上不禁一直在想, 终于恍然大悟了! 感觉十分有必要写一篇解释, 用自己的话说说kmp以及这个next. 一方面加深一下印象, 另一方面希望给偶然看到的人一点点启发 (
简介
首先, 如果我们用传统的方式来匹配这个字符串, 会得到如下的过程:
如果用KMP算法, 将减少无用的挪动 :
这么看可能还看不出什么, 如果我们稍微变化一下就可以看到KMP算法的巨大优势 :
对于上图这种匹配, 普通的暴力算法将远远落后于kmp
kmp工作机制
如果你不知道"前后缀" 也许以下的图能更好的帮助理解
上图来源于这里
匹配过程
为什么是刚好跳转到next[i]
比如上面这个图中, 接下来我们会将失配位置移动到P[2]也就是A的地方(右移两下), 如果我们少移, 是不可能匹配的, 不然的话公共前后缀长度会比当前的值大
next数组的编程求法
重点 : 弄明白j回溯的原理
建议对照代码观看 :
int i = 0, j = -1;
while(i < s.size()) {
if(s[i] == s[j] || j==-1) {
i++;
j++;
next.push_back(j);
}
else {
j = next[j]; // 如果s[i]!=s[j]说明匹配失败, 回到上一级公共前后缀处
}
}
我们列出两个相邻的指针i和j, 初始指在数组前和0号元素的位置
接下来我列出从0开始求出next数组的图示
这里再附上两个写的不错的链接
http://www.ruanyifeng.com/blog/2013/05/Knuth–Morris–Pratt_algorithm.html
https://www.bilibili.com/video/BV1Px411z7Yo?t=1068
好累啊
图解KMP以及next数组的求法的更多相关文章
- 转载-KMP算法前缀数组优雅实现
转自:http://www.cnblogs.com/10jschen/archive/2012/08/21/2648451.html 我们在一个母字符串中查找一个子字符串有很多方法.KMP是一种最常见 ...
- 求最长公共前缀和后缀—基于KMP的next数组
KMP算法最主要的就是计算next[]算法,但是我们知道next[]求的是当前字符串之前的子字符串的最大前后缀数,但是有的时候我们需要比较字符串中前后缀最大数,比如 LeetCode的shortest ...
- 06-01 Java 二维数组格式、二维数组内存图解、二维数组操作
二维数组格式1 /* 二维数组:就是元素为一维数组的一个数组. 格式1: 数据类型[][] 数组名 = new 数据类型[m][n]; m:表示这个二维数组有多少个一维数组. n:表示每一个一维数组的 ...
- 【bzoj2384】[Ceoi2011]Match 特殊匹配条件的KMP+树状数组
题目描述 给出两个长度分别为n.m的序列A.B,求出B的所有长度为n的连续子序列(子串),满足:序列中第i小的数在序列的Ai位置. 输入 第一行包含两个整数n, m (2≤n≤m≤1000000). ...
- HDU - 4763 Theme Section (KMP的next数组的应用)
给定一个字符串,求出一个前缀A,使得字符串的构成可以表示成ABABA的形式(B可以为空串). 输出这个前缀的最大长度. KMP算法Next数组的使用. 枚举中间的每个位置,可以根据Next数组求出这个 ...
- POJ 2752 KMP中next数组的应用
题意: 让你从小到大输出给的字符串中既是前缀又是后缀的子串的长度. 思路: 先要了解这个东西: KMP中next数组表示的含义:记录着字符串匹配过程中失配情况下可以向前多跳几个字符,它描述的也是子串的 ...
- KMP(next数组的更新理解)Codeforces Round #578 (Div. 2)--Compress Words
题目链接:https://codeforc.es/contest/1200/problem/E 题意: 有n串字符串,让你连起来:sample please ease in out ---> ...
- UVA 11475 Extend to Palindrome (kmp || manacher || 后缀数组)
题目链接:点击打开链接 题意:给你一个串,让你在串后面添加尽可能少的字符使得这个串变成回文串. 思路:这题可以kmp,manacher,后缀数组三种方法都可以做,kmp和manacher效率较高,时间 ...
- KMP中next数组的理解
next数组是KMP的核心,但对于next数组我们总是有时候感觉明白了,但有时候又感觉没明白,现在我就说下我自己对KMP中next数组的理解,首先next[i]上的数字的意义,next[i]表示的是当 ...
随机推荐
- BZOJ1059 二分匹配
1059: [ZJOI2007]矩阵游戏 Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 4810 Solved: 2297[Submit][Stat ...
- hdu3861他的子问题是poj2762二分匹配+Tarjan+有向图拆点 其实就是求DAG的最小覆盖点
The King’s Problem Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Other ...
- 一看就懂之吐血整理的 Docker 学习笔记
前言 随着devops的兴起,Docker 近年来越来越火,容器化概念也越来越火.此篇将带你瞬间入门Docker. Docker 概述 Docker 出现的背景 在我们的开发过程中,通常是这样的一种流 ...
- DevOps生命周期,你想知道的全都在这里了!
在大多数情况下,软件应用程序开发由于其规范性和复杂性而变得很耗时. 为了在短时间内交付高质量应用程序,软件开发人员正在遵循一套通用的实践,称为DevOps生命周期. 那么,DevOps在软件应用程序开 ...
- mysql排序,同样的语句 查询结果不一样的问题
一个项目,某段数据顺序出现异常导致运行异常.早期没有问题,用开发版本也没有问题,同样的查询排序语句在mysql客户端执行也没有问题. 这个排序不一致问题,这里记录下. 如下查询语句,根据‘order’ ...
- [SD心灵鸡汤]002.每月一则 - 2015.06
1.用最多的梦面对未来 2.自己要先看得起自己,别人才会看得起你 3.一个今天胜过两个明天 4.要铭记在心:每天都是一年中最美好的日子 5.乐观者在灾祸中看到机会:悲观者在机会中看到灾祸 6.有勇气并 ...
- 快速复习C语言 - 1变量与运算符
变量与运算符 本篇以读者知道 int.char.float.double 等数据类型为前提条件. float 类型注意事项 float 类型数没有办法跟一个数真正比较是否相等,可以定义借助绝对值在一定 ...
- Alpha冲刺 —— 5.4
这个作业属于哪个课程 软件工程 这个作业要求在哪里 团队作业第五次--Alpha冲刺 这个作业的目标 Alpha冲刺 作业正文 正文 github链接 项目地址 其他参考文献 无 一.会议内容 1.展 ...
- Chisel3 - util - LFSR16
https://mp.weixin.qq.com/s/DSdb4tmRwDTOki7mbyuu9A 实现16位线性反馈移位寄存器.可用于生成简单的伪随机数. 参 ...
- Java实现 LeetCode 724 寻找数组的中心索引(暴力)
724. 寻找数组的中心索引 给定一个整数类型的数组 nums,请编写一个能够返回数组"中心索引"的方法. 我们是这样定义数组中心索引的:数组中心索引的左侧所有元素相加的和等于右侧 ...