KMP算法-如何理解

相关主题
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

对KMP算法的理解

整理者——戴红伟

字符匹配算法的现实意义:随着互联网的日渐庞大,信息也是越来越多,如何在海量的信息中快速查找自己所要的信息是网络搜索研究的热点所在,在这其中,字符串匹配算法起着非常重要的作用,一个高效的字符串匹配算法,可以极大的提高搜索的效率和质量。

(请同时参照课本P53~54相关内容)

1.要理解next[j]=k 中,k的含意;

(1)BF算法

假设有字符串

S=S1S2......S N

P=P1P2......P M

其中(M

所以算法要点如下:

假设从S中i点开始扫描(也就是从S[i]开始,此时用一个变量k=i),顺序比较S[i]和P[1],S[i+1]和P[2]。这样,当P进行到第j个字符也就是P[j]的时候,发现S[i+j-1]和P[j]不匹配,那么需要把S的指针i回朔到S起始的下一个字符也就是k+1继续比较。

如图:

以上就是模式匹配的基本算法,这种算法对于大多数的匹配来说基本是O(N+M)的时间复杂度。

但是对于如下的字符串:

S=0000000000000000000000000000001

P=000001

这种字符串来说,每次匹配失败都是在P到最后一个字符也就是j=M的时候,此时S 的指针又必须回朔,导致大量的匹配。此时的时间复杂度是O(N*M)。

所以基本算法的时间复杂度是O(N*M)。当然了,对于大多数的匹配是不会有这么高的时间复杂度的,所以这种算法现在也在广泛使用,因为简单。

(2)KMP算法

为了解决上述的问题,KMP算法被发现。

KMP算法的思想如下。匹配过程中,出现不匹配时,S的指针不进行回朔(原地不动),将P尽可能地向后移动一定的距离,再进行匹配。

如图:

(该图引用自互联网)

从上图中我们看到,当S移动到i,P到j的时候失配。这时候i不回朔,而只是将P 向前移动尽可能的距离,继续比较。

假设,P向右移动一定距离后,第k个字符P[k]和S[i]进行比较。

此时如上图,当P[j]和S[i]失配后,i不动,将P前移到K,让P[k]和S[i]继续匹配。现在的关键是K的值是多少?

通过上图,我们发现,因为黄色部分表示已经匹配了的结果(因为是到了S[i]和P[j]的时候才失配,所以S i-j+1S i-j+2…S i-1 = P1P2…P j-1,见黄色的部分)。所以有:

1、S i-k+1S i-k+2…S i-1 = P j-k+1P j-k+2…P j-1。

所以当P前移到K时,有:

2、S i-k+1S i-k+2…S i-1 = P1P2…P k-1。

通过1,2有

P j-k+1P j-k+2…P j-1 = P1P2…P k-1。

呵呵,此时我们的任务就是求这个k值了。。。

参考:/2008-09/122068902261358.html

2.求出k 值

按照课本的求法就可以处理。

课本是已知前j个元素的“前缀函数值”,如何求的j+1个元素的前缀函数值。这里有一个思路要发生转变的地方,把一个模式串分成两个部分,因为我们要找k使得P j-k+1P j-k+2…P j-1= P1P2…P k-1,而这本身就是一个模式匹配问题,所以把模式串的前边部分的子串当作“新的模式串”,这样就很容易理解为什么当t k!=t j时,t1…t next[k]-1 = t j-(next[k]-1)…t j-1了。因为这时候t k匹配失败,需要进一步移动模式子串,所以移动的位置就是next[k]。

相关文档
最新文档