您的位置:首页 > 其它

[模板]AC自动机 洛谷3808 AC自动机

2018-01-12 21:12 239 查看

题目

AC自动机模板题

分析

AC自动机就是字典树的思想加上kmp思想的产物。。。

多画图就懂了。

来一波链接——AC自动机

code

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<cmath>
#include<queue>
#include<algorithm>

using namespace std;

struct Tree{
int fail;
int vis[26];
int num;
}ac[1000000];
int n;
int cnt=0;

void Build(string s)
{
int l=s.length();
int now=0;
for(int i=0;i<l;++i)
{
if(ac[now].vis[s[i]-'a']==0) ac[now].vis[s[i]-'a']=++cnt;
now=ac[now].vis[s[i]-'a'];
}
ac[now].num+=1;
}

void Get_fail()
{
queue<int> Q;
for(int i=0;i<26;++i)
{
if(ac[0].vis[i]!=0)
{
ac[ac[0].vis[i]].fail=0;
Q.push(ac[0].vis[i]);
}
}
while(!Q.empty())
{
int u=Q.front();
Q.pop();
for(int i=0;i<26;++i)
{
if(ac[u].vis[i]!=0)
{
ac[ac[u].vis[i]].fail=ac[ac[u].fail].vis[i];
Q.push(ac[u].vis[i]);
}
else ac[u].vis[i]=ac[ac[u].fail].vis[i];
}
}
}

int ac_Query(string s)
{
int l=s.length();
int now=0,ans=0;
for(int i=0;i<l;++i)
{
now=ac[now].vis[s[i]-'a'];
for(int t=now;t&&(ac[t].num!=-1);t=ac[t].fail)
{
ans+=ac[t].num;
ac[t].num=-1;
}
}
return ans;
}

int main()
{
cin>>n;
for(int i=1;i<=n;++i)
{
string s;
cin>>s;
Build(s);
}
ac[0].fail=0;
Get_fail();
string s;
cin>>s;
cout<<ac_Query(s)<<endl;
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: