zoukankan      html  css  js  c++  java
  • DSA——KMP算法字符匹配

    ////3.26日有感!

    不管看多少博文,关于KMP,都不如花些时间去看严老师的讲解视频有效果,

    上:http://v.youku.com/v_show/id_XODYxNjExODQ=.html     第 34分钟开始 

    下:http://www.56.com/u28/v_NjAwMzA0ODA.html     

    严蔚敏

    虽然严老师讲话速度慢些,最开始会觉得不耐烦,甚至想快进什么的,但是对我而言,正因为脑袋不那么太灵光才会看那么多都不懂,严老师慢慢的讲解正好弥补了

    我跟不上思路的毛病!简直完美!

    目标字符串 T

    模式字符串 P

    朴素的匹配算法很好懂,就是先比较T和P的第一位如果不匹配就把P后移一位····

    而KMP算法---的确如很多博客所言有点难理解诶,尝试过找个视频···不过http://www.ruanyifeng.com/blog/2013/05/Knuth%E2%80%93Morris%E2%80%93Pratt_algorithm.html

    看完 仍觉得部分匹配表的部分不是很清晰,继续查

    http://blog.csdn.net/itsenlin/article/details/21491787

    理解了一下做此记录

    模式P:       A B C D A B D

    部分匹配值:0 0 0 0  1  2 0

    怎么得到的呢

    是以第一个字符当前字符 的前缀 和后缀 的最长的共有元素的长度

    A:“A”的前缀null,后缀 null------没有共有元素-----长度=0

    B: “AB”的前缀[A] 后缀[B]------没有共有元素----长度=0

    C:“ABC”的前缀[A,AB],后缀[BC,C]------没有共有元素------长度=0

    D:“ABCD”的前缀[ABC,AB,A],后缀[BCD,CD,D]------没有·····长度=0

    A:“ABCDA”前缀[ABCD,ABC,AB,A],后缀[BCDA,CDA,DA,A]-----有共有元素了!A!所以最长共有元素长度!=1

    B:“ABCDAB”前缀[ABCDA,ABCD,ABC,AB,A]后缀[BCDAB,CDAB,DAB,AB,B]---还有共有元素,只有一个 是AB 长度=2,所以最长的=2

    D:“ABCDAB,ABCDA,ABCD,ABC,AB,A” [BCDABD,CDABD,BABD,ABD,BD,D]-----共有元素。。没有,所以=0

    根据反证法【具体咋证明的我也没证····】

    next[j+1]<=next[j]+1;

    特别的,当且仅当p[j]=p[next[j]]时候,取等号 即 next[j+1]==next[j]+1

    原因如下:还是没太搞清楚原因。http://www.xuetangx.com/courses/TsinghuaX/30240184_2015X/2015_T1/courseware/4c294e9ea5b5433d831443e64f64bacb/b8b4418bdde34788ae4184a9e31c4b42/

    P模式串 P[0,j-1],   (j),    P[j,m]

                  P模式串P[0,next[j] ],     (j+1),      P[j+2,m]

    *号代表配上的了,而

    所以根据这一点就可以用递推,来计算next[]了

     public int KMP(String P,String T)
       {
           int[] next=buildNext(P);
           int pLength=P.length();
           int tLength=T.length();
           int p=0,t=0;//作为类似指针的东西
          while(t<tLength&&p<pLength)
          {
              if(p<0||P.charAt(p)==T.charAt(t))
              {
                  t++;
                  p++;
              }
              else p=next[p];
          }
          return t-p;
       }


    public int[] buildNext(String p) { int j=0; int pLength=p.length(); int next[]=new int[p.length()]; int t=next[0]=-1; while(j<pLength-1) { if(0>t||p.charAt(j)==p.charAt(t))//匹配 { next[++j]=++t; } else t=next[t];///失配 } return next; }
  • 相关阅读:
    可持久化BCJ
    Codeforces 911 三循环数覆盖问题 逆序对数结论题 栈操作模拟
    找不同
    最接近的三数之和
    找到所有数组中消失的数字
    三数之和
    小程序中的变量
    二叉树的最近公共祖先
    深拷贝和浅拷贝
    下载安装JDK
  • 原文地址:https://www.cnblogs.com/Cherrylalala/p/6576016.html
Copyright © 2011-2022 走看看