//AC自动机有很多写法,这种写法是比较稳的。
#include<iostream>
#include<cstdio>
#include<queue>
using namespace std;
const int maxn=1e6+6;
int n;
string S[maxn],T;
int sz=1,trie[maxn][30],cnt[maxn*30],fail[maxn*30];
inline void insert(string s){
int p=0;
for(register int i=0;i<s.size();++i){
if(!trie[p][s[i]-'a'+1])trie[p][s[i]-'a'+1]=++sz;
p=trie[p][s[i]-'a'+1];
}
++cnt[p];
}
inline void bfs(void){
queue<int>q;
for(register int i=1;i<=26;++i){
if(trie[0][i])q.push(trie[0][i]),fail[trie[0][i]]=0;
}
while(q.size()){
int x=q.front();q.pop();
for(register int i=1;i<=26;++i){
if(!trie[x][i])trie[x][i]=trie[fail[x]][i];
else{
q.push(trie[x][i]);
fail[trie[x][i]]=trie[fail[x]][i];
}
}
}
}
inline int find(){
int p=0,ans=0;
for(register int i=0;i<T.size();++i){
p=trie[p][T[i]-'a'+1];
for(register int t=p;t&&~cnt[t];t=fail[t])ans+=cnt[t],cnt[t]=-1;
}
return ans;
}
int main(){
cin>>n;
for(register int i=1;i<=n;++i){
cin>>S[i];
insert(S[i]);
}
cin>>T;
bfs();
printf("%d\n",find());
return 0;
}
原文:https://www.cnblogs.com/little-aztl/p/11159608.html