字串 擴充套件kmp演算法總結

2021-08-05 23:56:55 字數 3062 閱讀 1250

這兩天呢,一直在被小夥伴們快ak的恐懼支配,g題杭電的資料很水,但是自己還是選擇不水過,用擴充套件kmp去寫,網上的資料很多,自己選了乙個最簡潔的模板,不用再寫乙個求next陣列的函式,直接呼叫前特殊處理下exkmp函式就既可以求next陣列,又可以求ex陣列啦,hh誰說魚與熊掌不可兼得,這不就是嗎~但是呢,一開始一點也不好理解哎,自己選的模板,跪著也得理解完~~~(淚目~~

————言歸正傳,總結——————

1.擴充套件kmp演算法呢是對kmp演算法的擴充套件,擴充套件kmp演算法也有乙個和kmp函式名字一樣的next陣列,還有乙個ex陣列。

2.擴充套件kmp演算法的可以用o(m+n)的複雜度求出字串s1任意字尾和字串s2的最長公共字首。

3:擴充套件kmp演算法裡ex陣列:ex[i] == j表示s1

以i為起始的字尾與s2的最長公共字首。

擴充套件kmp演算法裡next陣列:next[i] == j表示s2以i為起始的字尾與s2的最長公共字首

兩者作用都一樣當然可以呼叫同乙個函式咯~

kmp演算法裡next陣列:next[i] == j表示s2在0~i之前已匹配的字首字尾長度為j+1(前提是next[0]初始化為-1,如果初始化為0,已匹配的長度就為j)

————加深理解,模擬演算法實現過程————

用樣例s1=aaaabaa,s2=aaaaa直接進行模擬演算法實現過程,前提是要結合模板

第一步:由於exkmp函式的作用是在已知s2的next陣列的情況下,求出字串s1的任意字尾與字串s2的最長公共字首,存入ex,所以我們需要先呼叫函式求出next陣列

主函式裡呼叫過程如下,預先初始化next[0]=0;

exkmp(s2+1,s2,next+1,next);

這樣呼叫的原因參見總結3,生成next陣列的過程相當於將s2與s2自身進行匹配,s2+1     == 形參s1

s2        == 形參s2

next+1 == 形參ex

next     == 形參next.

接收過程如下:

void exkmp(char s1,char s2,int ex,int next)

a.在此函式中我們傳遞給形參s1的是s2+1,結合下圖所示樣例s1=aaaa,s2=aaaaa來看,即s1[0..] == (s2+1)[1..]

b.傳遞給形參ex的是next+1,也就是next陣列後移一位,即ex[i] == next[i+1](有點難懂,解釋下,

我們將形參s1和形參s2進行匹配時,實際就是實參陣列s2[1...]的字尾與實參陣列本身s2[0..]的字首進行匹配,所以我們匹配出的最大公共長度min(next[j],p)賦值給形引數組ex[i]時,實際就是賦值給next[i+1],(這裡不知道為什麼取最小值不要緊,稍後進行解釋),結合下圖兩張來看,明顯e陣列的值存入next陣列的後一位。

第二步:在已知s2的next陣列的情況下,再次呼叫函式,求出s1的任意字尾和s2的最長公共字首,存入ex。

在函式呼叫過程中,我們比較s1[i..]與s2的最長公共字首部分時,只取較小的值,原因是,只有s2的自身字首長度與p(s2和s1的公共字首長度)都是公共長度的時候,這個值才能保證就是s1[i..]與s2的最長公共字首部分。

當它們相等時,無法直接比較判斷出最長公共字首部分,因為p之後也有可能有公共長度,所以我們只需要繼續從p開始逐一比較。

/*主函式裡初始化和呼叫*/

/*next[0] = 0;

exkmp(s2+1,s2,next+1,next);

exkmp(s1,s2,ex,next);*/

void exkmp(char s1,char s2,int ex,int next)

else if(next[j] < p)

ex[i] = next[j];

else if(next[j] > p)

ex[i] = p;

else

i++;

j++;

p--;

} ex[i] = 0;

return;

}

字串專題 擴充套件KMP

思路 乍一看就是擴充套件kmp,但這題還是要一點點轉化。如果想要滿足題目要求,匹配段肯定間隔是相反的。比如樣例中在0位置匹配 1 3 4 2 6 9 5 3 2 2 0 code include using namespace std const int ax 1e5 66 int n m int ...

( 字串專題 ) 擴充套件KMP

字串專題 擴充套件kmp 時間複雜度 o n m 用 extend i 表示t i n 1 與p的最長公共字首。假設t aaaab p aaaa 則extend 5 next i 表示為 串p 中以 i 為起點的字尾字串和 整個串p 的最長公共字首長度.假設p aaaab 則next 5 模板 in...

字串 KMP演算法

而kmp演算法在字串匹配方法中乙個很著名並且很聰明的演算法,當然也確實比較難理解。甚至於有程式設計師因為無法理解kmp演算法而直接改用暴力匹配。本身自己學演算法起步較晚,第一次接觸到kmp演算法已經是研究生畢業一年了。雖然帶著研究生的學歷背景,但是剛開始看的時候依然是一臉懵逼。看了很多博主的講解總算...