總結 字串 AC自動機 KMP演算法

2021-08-29 16:21:40 字數 1693 閱讀 6882

ac自動機與kmp演算法,都是用於優化字串匹配的演算法。

kmp演算法應用於單模式串的匹配。

而ac自動機是應用於多模式串的匹配。

但並不意味著kmp演算法可以被完全取代(儘管兩者的演算法思想本質上是一樣的)。

相對而言,kmp演算法比較容易一些。

首先,考慮如何暴力匹配?很顯然,可以以主串的任意乙個位置開頭,然後開始匹配,失配後,再找下乙個位置開頭。

這樣的複雜度顯然是o(n*m)的。非常低劣。

而kmp演算法則是用於優化這個過程的。顯然,每次重新匹配時,如果能利用之前匹配的資訊,那麼就會節約很多時間。這裡就要引入fail陣列。fai

li

fail_i

faili​

表示與字首i

ii擁有相同字尾的,最靠後的位置。這樣如果在i號位置失配,那麼可以跳到其fail指標的位置,繼續匹配。

這樣做的複雜度很顯然就是o(n+m)的。

板子:

void

build

(int x)

else

j=fail[j];}

}void

solve

(int x)

else

j=fail[j];if

(j==len[x]

) ch[i-len[x]]|

=(1<<

(x-1))

;}}

1、bzoj4974字串大師

2、bzoj3670動物園

3、bzoj4560字串覆蓋

4、bzoj4820硬幣遊戲

5、bzoj2384[ceoi2011]match

ac自動機則是將fail指標帶到了trie樹上。

原理還是一樣的。fai

li

fail_i

faili​

與i

ii擁有相同字尾的深度最大的點。

每次失配後也是往著fai

li

fail_i

faili​

跑。1、bzoj1444有趣的遊戲

2、bzoj1559密碼

3、bzoj4861魔法咒語

板子:

struct nodetree[maxn]

;node* rt=tree,

*ncnt=tree;

void

insert

(node *now,

char

*c,int id)

int d=

*c-'a';if

(now-

>ch[d]

==null

)insert

(now-

>ch[d]

,++c,id);}

queue> q;

void

build()

while

(x!=rt&&x-

>ch[i]

==null

) x=x-

>fail;

if(x-

>ch[i]

==null

) now-

>ch[i]

->fail=rt;

else

now-

>ch[i]

->fail=x-

>ch[i];}

}}

AC自動機模版 字串

ac自動機主要用於解決多模式串的匹配問題 具體指的是 如下圖中 模式串 p中有多個 字串,問這些字串在 主串s的出現的總次數 是字典樹 trie樹 的變種,一種偽樹形結構 主體是樹形的,但是由於加入了失敗指標,使得它變成了乙個有向圖 以當前節點為終點的 模式字串 的數量 int fail 1 fai...

kmp與ac自動機

xj比賽做到一道字串題,結果發現想打個字串匹配都只會n 2了,又一次忘記了kmp 想必是當初學這玩意心理陰影面積太大了。這裡再梳理一遍kmp和ac自動機 以便下次再忘了有地方看.kmp 用於處理對於字串s,想知道它在另外某個串哪些位置出現的問題,先做預處理得到乙個失配陣列,這個陣列第i位表示s的前i...

字串 2 AC自動機

ac自動機,其實就是trie樹與kmp的結合,且有dfa 有限狀態機 的性質.理解的關鍵點 1.fail指標 起到回溯作用 2.每次匹配都是主串不動,移動指標now去回溯找字尾的字首 3.乙個優化點,將null指向root 編碼更簡單.考察時一般也會問道dfa的性質.ac自動機解決問題 1.多模式串...