zoukankan      html  css  js  c++  java
  • BM模式匹配算法原理(图解)

       

    BM模式匹配算法原理(图解)

    首先,先简单说明一下有关BM算法的一些基本概念。

    BM算法是一种精确字符串匹配算法(区别于模糊匹配)。

    BM算法采用从右向左比较 的方法,同时应用到了两种启发式规则,即坏字符规则 和好后缀规则 ,来决定向右跳跃的距离。

    BM算法的基本流程: 设文本串T,模式串为P。首先将T与P进行左对齐,然后进行从右向左比较 ,如下图所示:

        若是某趟比较不匹配时,BM算法就采用两条启发式规则,即坏字符规则 和好后缀规则 ,来计算模式串向右移动的距离,直到整个匹配过程的结束。       

    下面,来详细介绍一下坏字符规则 和好后缀规则 。

         首先,诠释一下坏字符和好后缀的概念。

       请看下图:

         图中,第一个不匹配的字符(红色部分)为坏字符,已匹配部分(绿色)为好后缀。

        1)坏字符规则(Bad Character):

              在BM算法从右向左扫描的过程中,若发现某个字符x不匹配,则按如下两种情况讨论:

                   i. 如果字符x在模式P中没有出现,那么从字符x开始的m个文本显然不可能与P匹配成功,直接全部跳过该区域即可。

                   ii. 如果x在模式P中出现,则以该字符进行对齐。

             用数学公式表示,设Skip(x)为P右移的距离,m为模式串P的长度,max(x)为字符x在P中最右位置。

                    

           例1:

             下图红色部分,发生了一次不匹配。

                   

       

            计算移动距离Skip(c) = 5 - 3 = 2,则P向右移动2位。

            移动后如下图:

                

       

              

        2)好后缀规则(Good Suffix):

             若发现某个字符不匹配的同时,已有部分字符匹配成功,则按如下两种情况讨论:

                  i. 如果在P中位置t处已匹配部分P'在P中的某位置t'也出现,且位置t'的前一个字符与位置t的前一个字符不相同,则将P右移使t'对应t方才的所在的位置。

                  ii. 如果在P中任何位置已匹配部分P'都没有再出现,则找到与P'的后缀P''相同的P的最长前缀x,向右移动P,使x对应方才P''后缀所在的位置。

             用数学公式表示,设Shift(j)为P右移的距离,m为模式串P的长度,j 为当前所匹配的字符位置,s为t'与t的距离(以上情况i)或者x与P''的距离(以上情况ii)。

                 

       

           以上过程有点抽象,所以我们继续图解。

             例2:

              下图中,已匹配部分cab(绿色)在P中再没出现。

               

       

             再看下图,其后缀T'(蓝色)与P中前缀P'(红色)匹配,则将P'移动到T'的位置。

               

       

             移动后如下图:

                

              自此,两个规则讲解完毕。

         在BM算法匹配的过程中,取SKip(x)与Shift(j)中的较大者作为跳跃的距离。

         BM算法预处理时间复杂度为O(m+s),空间复杂度为O(s),s是与P, T相关的有限字符集长度,搜索阶段时间复杂度为O(m·n)。

    最好情况下的时间复杂度为O(n/m),最坏情况下时间复杂度为O(m·n)。

  • 相关阅读:
    Max Sum Plus Plus HDU
    Monkey and Banana HDU
    Ignatius and the Princess IV HDU
    Extended Traffic LightOJ
    Tram POJ
    Common Subsequence HDU
    最大连续子序列 HDU
    Max Sum HDU
    畅通工程再续
    River Hopscotch POJ
  • 原文地址:https://www.cnblogs.com/fuyou/p/3233291.html
Copyright © 2011-2022 走看看