KMP算法理解

传说中的 看毛片算法~~~,嘿嘿嘿

推荐博客,讲的很好

http://www.ruanyifeng.com/blog/2013/05/Knuth%E2%80%93Morris%E2%80%93Pratt_algorithm.html

http://www.cnblogs.com/10jschen/archive/2012/08/21/2648451.html

http://blog.csdn.net/yutianzuijin/article/details/11954939

先上代码

// MyKMP.cpp : Defines the entry point for the console application.
//

#include "stdafx.h"
#include <IOSTREAM>
#include <VECTOR>

using namespace std;

void getnext(string pattern,vector<int> & next){
    if(next.size() < pattern.size())
        next.resize(pattern.size());
    next[0] = 0;
    int i = 0;
    int k = 0;
    for(i = 1;i<pattern.size();i++){
        while(k>0 && pattern[k]!= pattern[i])//递归找子对称,看已匹配的next[k-1]的后一项(即pattern[k])是否与pattern[i]相同
            k = next[k-1];
        
        if(pattern[k] == pattern[i])   //如果遇到相同的,加一处理
            k++;
        
        next[i] = k;
    }
}
int KMP(string des,string pattern){
    vector<int> next;
    getnext(pattern,next);
    int i,q;
    for(i = 0,q = 0;i<des.size();i++){
        while(q>0 && des[i] != pattern[q])//看已匹配的next[k-1]的后一项(即pattern[k])是否与des[i]相同
            q = next[q-1];
        
        if(des[i] == pattern[q])
            q++;
        
        if(q == pattern.size())
            return i - pattern.size() + 1; 
    }
    return -1;
}

int main(int argc, char* argv[])
{
    cout<<KMP("ababdababcda","ababc")<<endl;
    return 0;
}

getnext,获取next数组,这应该说是最关键的

1,   abcab

     abcab  

  当添加一个字符时,

    abcabc

       abcabc

  只需比较最后一个字符和之前已匹配的后一个字符是否相同,相同就加1,如上图所示

  若不同,则不断找子对称,看已匹配的next[k-1]的后一项(即pattern[k])是否与pattern[i]相同,可以画个图自己看看,这里不太好弄

 

2 KMP过程中,若有不匹配处,查next表得知next[i] ,得到跳跃值,移动位数 = 已匹配的字符数 - 对应的部分匹配值

  即比较pattern[ next[q-1] ] 与des[i] 即可,不同则继续此步骤进行迭代

 

posted @ 2015-08-06 14:46  朽木可雕否  阅读(148)  评论(0编辑  收藏  举报