博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
串的模式匹配算法——“KMP算法”
阅读量:4478 次
发布时间:2019-06-08

本文共 1554 字,大约阅读时间需要 5 分钟。

写在文章前:我写这篇文章,一来为了整理和记录自己对KMP算法的一些理解,二来分享给大家学习和交流。2016-03-13

  1.何谓KMP算法?——粗略介绍

     这种算法是D.E.Knuth、J.H.Morris 和 V.R.Pratt 同时发现的,所以各取他们名字的首字母命名这个算法——KMP。它是解决串的模式匹配问题的一种算法,举个例子说明一下KMP算法是解决什么问题的:比如字符串(主串) abbcabcabcbc , 子串(模式串) bcabcb ,在主串中找出字串的第一个字符出现的位置(匹配结果明显是6)。

   这个问题的解法,最简单的就是可以采用枚举法,所谓的BF算法。

            

        对比于BF算法,KMP算法在匹配策略上做出了一些改进。KMP算法在每一趟匹配过程中出现不等时,可以利用已经得到的“部分匹配”的结果将模式向右“滑动”到下一个最佳尝试位置,然后继续比较.

      

  2.KMP原理详解

    KMP利用了已有的匹配结果,在主串与模式串不匹配时一下子滑动到已匹配的模式串前段中某个位置,直接可以继续匹配该位置后的串,而不需担心前面的串。我们可以观察下串的匹配过程。

    

    其实,框3和框4的匹配情况只跟模式串有关,所以我们可以在模式匹配前先通过模式串得到模式串中各元素下次匹配的最佳位置,因为每个元素都可能出现不匹配情况,所以需要保存有所有元素的下次匹配位置,即求出kmp算法中的next数组。什么是next数组?我们定义next数组为,next[i]表示的是当主串的k位置与模式串的i位置不匹配时(主串长〉k〉=i),主串k位置下一步应该与模式串的next[i]位置进行匹配。怎么求next数组?next[j]= 模式串前段p1 ··· pj-1中头尾相同的最长头串或尾串的长+1。(注:头串简称以串头元素开头的串,尾串简称以串尾元素结尾的串。)                                             

  1.            next[j]=  0      当j =1时
  2.        next[j]= max{k|0<k<j , p1 ··· pk-1 =pj-k+1···pj-1}   //这个式子等同于模式串P1~Pj-1的头串与自身(p1~pj-1)的尾串进行模式匹配,只不过这里是得到被匹配的串(P1-Pk-1)的串长+1,即k。
  3.            next[j]=  1      除了1、2情况之外的其他情况 

比如:

 j 1 2 3 4 5 6 7 8 9
 p[j] a b a a b c a b c
  0                
    1              
      1            
  -   - 2          
      - 2        
  - -   - - 3      
              1    
            - 2  
   - -         - - 3
 next[j] 0 2 2 3
 j 1 2 3 4 5 6 7 8 9
 p[j] a a a a a a a a a
  0                
  - 1              
  - - 2            
  - = - 3          
  - = = - 4        
  - = = = - 5      
  - = = = = - 6    
  - = = = = = - 7  
  - = = = = = = - 8
 next[j]  0

 

               

  3.KMP算法编码

void getNext(char* pattern,int* next){    //填充模式串的next数组,原理也是kmp算法的原理。    int i=1,j=0;                        //用i作为主串下标,j作为模式串的下标。    next[1]=0;    while(i
pattern[0]) return i-pattern[0]; else return 0;}

 

转载于:https://www.cnblogs.com/lyyinger/p/5271424.html

你可能感兴趣的文章
【转】 Pro Android学习笔记(六七):HTTP服务(1):HTTP GET
查看>>
获取子iframe框架的元素
查看>>
WordCount bug修复录
查看>>
承载进程 (vshost.exe)
查看>>
[转]WPF MVVM 实战
查看>>
[转载] Python 标准库 urllib2 的使用细节
查看>>
Silverlight使用DataGrid的模板列(DataGridTemplateColumn)实现类似TreeListView控件的效果
查看>>
Java学习——Applet写字符串(调字体)
查看>>
react路由
查看>>
nyoj 220——推桌子——————【贪心】
查看>>
java 静态方法分析
查看>>
codevs——4189 字典&&HihoCoder #1014 : Trie树
查看>>
洛谷——P1602 Sramoc问题
查看>>
【MySQL笔记】字符串、时间日期转换
查看>>
jQuery实战之仿淘宝商城左侧导航效果
查看>>
AC日记——「SCOI2016」幸运数字 LiBreOJ 2013
查看>>
unmount
查看>>
数据库连接池
查看>>
javascript获得和设置以及移除元素属性的三个方法
查看>>
windwos iis 7.5 使用html 报405错误
查看>>