字符串匹配算法之KMP

KMP是单模匹配算法,主串是S,模式串是P,查找P在S中出现的位置。

主要是思想是主串的索引 i 递增,当主串与模式串发生不匹配时,把模式串右移,右移的位数为 j – fail[j] ,对于模式串计算fail函数,这个函数用来表示计算模式串某个位置发生失配时,模式串重新匹配的位置。

fail应该指向最后一个可能产生匹配的地方,P[1..fail[j]-1]是P[1..j-1]的最长相等前缀后缀。

有个优化的地方:如果P[j]和P[fail[j]]是同一个字符,那么回溯后马上又匹配失败,可以直接令fail[j] = fail[fail[j]]。

c++代码示例:

计算fail函数代码:

#include<iostream>
using namespace std;

// kmp fail array
void computefailure(int fail[],int n,char p[]){
    int j = 0;
    for(int i = 1;i<=n;i++){
        if(p[i] == p[j])
            fail[i] = fail[j];
        else
            fail[i] = j;
        while(j>0 && p[i]!=p[j])
            j = fail[j];
        j = j+1;
    }
}
int main()
{
    char p[] = {‘ ‘,‘A‘,‘B‘,‘B‘,‘A‘,‘B‘,‘B‘,‘A‘,‘B‘,‘A‘,‘B‘,‘B‘};
    int fail[20];
    int len = 11;
    computefailure(fail,len,p);
    for(int i=1;i<=len;i++)
        cout<<fail[i]<<endl;
    return 0;
}

KMP算法示例:

#include<iostream>
using namespace std;
const int MAX_N = 100;
int fail[MAX_N];

// kmp fail array
void computefailure(int fail[],int n,char p[]){
    int j = 0;
    for(int i = 1 ; i <= n ; i++){
        if( p[i] == p[j] )
            fail[i] = fail[j];
        else
            fail[i] = j;
        while( j>0 && p[i]!=p[j] )
            j = fail[j];
        j = j+1;
    }
}

int kmp(char T[],int n,char P[],int m){
    int j = 1;
    for (int i = 1; i <= n ; i++){
        while( j>0 && T[i] != P[j])
            j = fail[j];
        if( j == m )
            return i-m+1;
        j = j+1;
    }
    return -1;
}
int main()
{
    char T[] = {‘ ‘,‘A‘,‘B‘,‘B‘,‘A‘,‘B‘,‘B‘,‘A‘,‘B‘,‘A‘,‘B‘,‘B‘};
    char P[] = {‘ ‘,‘B‘,‘B‘,‘A‘};
    int lenT = 11;
    int lenP = 3;
    computefailure(fail,lenP,P);
    cout<<kmp(T,lenT,P,lenP)<<endl;
    return 0;
}

字符串匹配算法之KMP

时间: 2024-10-14 19:11:31

字符串匹配算法之KMP的相关文章

4种字符串匹配算法:BS朴素 Rabin-karp 有限自动机 KMP(上)

字符串的匹配的算法一直都是比较基础的算法,我们本科数据结构就学过了严蔚敏的KMP算法.KMP算法应该是最高效的一种算法,但是确实稍微有点难理解.所以打算,开这个博客,一步步的介绍4种匹配的算法.也是<算法导论>上提到的.我会把提到的四种算法全部用c/c++语言实现.提供参考学习.下图的表格,介绍了各个算法的处理时间和匹配时间.希望我写的比较清楚.如果不理解的,或者不对的,欢迎留言. 字符串匹配算法及其处理时间和匹配时间 算法 预处理时间 匹配时间 朴素算法 0 O((n-m+1)m) Rabi

字符串匹配算法KMP算法

数据结构中讲到关于字符串匹配算法时,提到朴素匹配算法,和KMP匹配算法. 朴素匹配算法就是简单的一个一个匹配字符,如果遇到不匹配字符那么就在源字符串中迭代下一个位置一个一个的匹配,这样计算起来会有很多多余的不符合的匹配做了冗余的比较.假设源字符串长n,字串长m 该算法最差时间复杂度为 m*(n-m+1),记为O(n*m);这里不做过多解释朴素匹配算法. KMP算法: kmp算法不是在源字符串中下手,他是从字串下手,比如我要在源字符串(acabaabaabcacaabc)中匹配一个字符串字串(ab

4种字符串匹配算法:BS朴素 Rabin-karp 有限自动机 KMP(中)

接着上文(地址),我们来聊一聊自动机算法(有限自动机字符串匹配算法)和KMP算法. ====#=有限自动机算法=#===== 关于有限自动机,网上的分析的资源,大部分都很笼统,算导上的知识点,全是数学公式,看的也会特别累.因此,打算从算导的第一题开始讲起.从习题入手,讲这个算法的思想. 例子:对模式 P = aabab构造出相应的字符串匹配自动机,并说明它在文本字符串T=aaababaabaababaab上的操作过程. 再讲这个例子之前,我们有必要先来了解一下自动机是什么意思? 有限自动机是什么

KMP字符串匹配算法——用最容易理解的方式描述

看了数据结构书上对于快速模式匹配算法KMP的介绍,感觉云里雾里.本文根据自己理解,并查资料整理了一种非常清晰简单的字符串匹配算法,并给予实现,自诩原创吧. 字符串匹配是我们经常要用到的一种算法,与普通的匹配算法相比KMP算法效率更高,时间复杂度为O(m+n).下面给予详细讲解: 概念详解 设原字符串为"BBC ABCDAB ABCDABCDABDE",待匹配字符串为"ABCDABD". 首先,字符串"BBC ABCDAB ABCDABCDABDE"

KMP字符串匹配算法及next前缀数组的应用

#KMP字符串匹配算法及next前缀数组的应用------ KMP算法通常是我们学习字符串匹配算法时遇见的第一个算法,另外还有Rabin-Karp, Sunday算法等. 相对于其他字符串匹配算法, kmp在字符串中字符重复率低的情况下并不具备优势,那为什么KMP算法会作为经典的教学算法呢? 原因可能是:KMP算法充分利用next前缀数组的信息来优化算法,减小时间复杂度的思路在很多字符串相关问题中能给我们启发. 首先上KMP字符串匹配算法, [leetcode在线测试地址](https://le

KMP字符串匹配算法翔解?

那么首先我们知道,kmp算法是一种字符串匹配算法,那么我们来看一个例子. 比方说,现在我有两段像这样子的字符串: 分别是T和P,很明显,P比T的长度要短很多,我们要做的事情呢,就是找找T中有没有和P相同的一段. 如果按照最简单的办法来做匹配的话,我们一般是一个一个字母的来做. 像这样: 很显然,图中前面3位都是能匹配的,而第四位却不能匹配,怎么办? 这样: 我们就会将整个P字符串向右移动一格,又重新开始,从T中b处与P中第一个a处开始匹配. 如此往复,显然这样是很慢的,因为我们来考虑考虑这样一种

字符串匹配算法

字符串匹配问题的形式定义: 文本(Text)是一个长度为 n 的数组 T[1..n]: 模式(Pattern)是一个长度为 m 且 m≤n 的数组 P[1..m]: T 和 P 中的元素都属于有限的字母表 Σ 表: 如果 0≤s≤n-m,并且 T[s+1..s+m] = P[1..m],即对 1≤j≤m,有 T[s+j] = P[j],则说模式 P 在文本 T 中出现且位移为 s,且称 s 是一个有效位移(Valid Shift). 比如上图中,目标是找出所有在文本 T=abcabaabcaba

多模字符串匹配算法之AC自动机—原理与实现

简介: 本文是博主自身对AC自动机的原理的一些理解和看法,主要以举例的方式讲解,同时又配以相应的图片.代码实现部分也予以明确的注释,希望给大家不一样的感受.AC自动机主要用于多模式字符串的匹配,本质上是KMP算法的树形扩展.这篇文章主要介绍AC自动机的工作原理,并在此基础上用Java代码实现一个简易的AC自动机. 欢迎探讨,如有错误敬请指正 如需转载,请注明出处 http://www.cnblogs.com/nullzx/ 1. 应用场景-多模字符串匹配 我们现在考虑这样一个问题,在一个文本串t

时空权衡之输入增强 ----字符串匹配算法Horspool算法和Boyer-Moore算法

在算法设计的时空权衡设计技术中,对问题的部分或者全部输入做预处理,对获得的额外信息进行存储,以加速后面问题的求解的思想,我们称作输入增强. 其中字符串匹配算法Horspool算法和Boyer-Moore算法就是输入增强的例子. 首先了解一下字符串匹配的概念.我们把在一个较长的n个字符的串中,寻找一个给定的m个字符的串的问题,称为字符串匹配问题.较长的串称为text,而需要寻找的串称为pattern. 字符串匹配问题的蛮力算法很好理解:我们把pattern与text第一个字符对齐,从左往右比较pa