{模板}AC自动机
2017-11-29 19:23
330 查看
先贴一个大白书的代码
来自这篇blog
自己的
刚开始一点也不注意常数
TLE了好久啊[淚]
来自这篇blog
//HDU2222 #include <queue> #include <cstdio> #include <cstring> #include <iostream> #include <algorithm> using namespace std; const int N=500500; struct ACautomachine { int chd [26];//孩子节点编号 int cnt ;//当前结点 表示字符串个数 int fail ;//失配指针 int last ,sz,ans;//题目需要 void init() { sz=1,ans=0; memset(cnt,0,sizeof(cnt)); memset(fail,0,sizeof(fail)); memset(chd[0],0,sizeof(chd[0])); } void insert(char* p)//构建trie { int cur=0; for(;*p;p++) { if(!chd[cur][*p-'a']) { memset(chd[sz],0,sizeof(chd[sz])); chd[cur][*p-'a']=sz++; } cur=chd[cur][*p-'a']; } cnt[cur]++; } bool query(char* p)//题目需要 { int cur=0; for(;*p;p++) { if(!chd[cur][*p-'a']) break; cur=chd[cur][*p-'a']; } return cnt[cur]&&(!(*p)); } int getFail() { queue<int> q; fail[0]=0; for(int c=0;c<26;c++) { int u=chd[0][c]; if(u) { fail[u]=0/*Null*/; q.push(u); last[u]=0; } } while(!q.empty()) { int r=q.front(); q.pop(); for(int c=0;c<26;c++) { int u=chd[r][c]; if(!u) { //直接指向 fail //也就是 把 trie树 的 chd[fail[r]][c]及其子孙 全部 “复制” 作r点的子孙 chd[r][c]=chd[fail[r]][c]; continue; } q.push(u); int v=fail[r]; while(v&&!chd[v][c]) v=fail[v]; //1. 令指针为 fail[fa[u]] //2. 若指针的一级儿子中存在一点(代表字符)与 u 相同 // 则令fail[u] 指向 当前指针的该儿子 //3. 否则 指针指向 fail[指针] 并重复 2 操作、 //目的:使得当前点及其到根的路径(即一个字典串) 与 fail 和fail[fail]... 所代表字典串 后缀相同 // 从而实现重新匹配 fail[u]=chd[v][c]; last[u]=cnt[fail[u]] ? fail[u] : last[fail[u]]; } } } void solve(int j) //题目需要 { if(!j) return; if(cnt[j]) { ans+=cnt[j]; cnt[j]=0; } solve(last[j]); } void find(char* T) //题目需要 { int n=strlen(T),j=0; getFail(); for(int i=0;i<n;i++) { j=chd[j][T[i]-'a']; if(cnt[j]) solve(j); else if(last[j]) solve(last[j]); } } }ac; int main() { int t,n; char dic[100],str[1100000]; scanf("%d",&t); while(t--) { ac.init(); scanf("%d",&n); while(n--) { scanf("%s",dic); ac.insert(dic); } scanf("%s",str); ac.find(str); printf("%d\n",ac.ans); } return 0; }
自己的
刚开始一点也不注意常数
TLE了好久啊[淚]
#include <ctime> #include <cmath> #include <cstdio> #include <cstring> #include <iostream> #include <algorithm> #define fo(i,x,y) for (int i=(x);i<=(y);++i) #define fd(i,x,y) for (int i=(x);i>=(y);--i) #define oo 2139062143 using namespace std; typedef long long ll; typedef double db; const int N=501000,C=27; int T,n; int ans; char dic[55],str[1100000]; struct AcAutoMation{ int d ; int chd [C]; int ot ; int fail ,next ,last ; int bz ; int sz; void del(int x) { next[last[x]]=next[x],last[next[x]]=last[x]; bz[x]=1; } void init() { memset(bz,0,sizeof bz); memset(chd[0],0,sizeof chd[0]); memset(ot,0,sizeof ot); memset(fail,0,sizeof fail); sz=0; } void insert(char *p) { int tmp=0; int len=strlen(p+1); fo(i,1,len) { int now=p[i]-'a'; if(!chd[tmp][now]) { chd[tmp][now]=++sz; memset(chd[sz],0,sizeof(chd[sz])); } tmp=chd[tmp][now]; } ++ot[tmp]; } void Getfail() { int tmp=0; int hd=0,tl=0; fo(i,0,25) { if(chd[0][i]) { d[++tl]=chd[0][i]; fail[chd[0][i]]=0; } } while(hd++<tl) { tmp=d[hd]; fo(i,0,25) if(chd[tmp][i]) { d[++tl]=chd[tmp][i]; int to=fail[tmp]; while(to!=0&&!chd[to][i]) to=fail[to]; fail[chd[tmp][i]]=chd[to][i]; next[chd[tmp][i]]=(ot[chd[tmp][i]])?(fail[chd[tmp][i]]):(next[fail[chd[tmp][i]]]); } } } void solve(char *p) { int tmp=0; int len=strlen(p+1); fo(i,1,len) { int now=p[i]-'a',to=tmp; while(!chd[to][now]&&to) to=fail[to]; tmp=chd[to][now]; for (int pp=tmp;pp;pp=next[pp]) { if(ot[pp]) { ans+=ot[pp],ot[pp]=0; } } } } }ac; int main() { int TT=clock(); scanf("%d\n",&T); while(T--) { ac.init(); scanf("%d\n",&n); fo(i,1,n) { scanf("%s\n",dic+1); ac.insert(dic); } ac.Getfail(); ans=0; scanf("%s\n",str+1); ac.solve(str); printf("%d\n",ans); } return 0; }
相关文章推荐
- HDU2222 Keywords Search 【AC自动机模板题】
- HDU 2222 Keywords Search(AC自动机模板)
- hdu 3695 AC自动机模板题
- P3808 【模板】AC自动机(简单版)
- HDU2222 AC自动机模板
- AC自动机(模板)
- AC自动机模板
- HDU2222 AC自动机 入门模板
- HDU 2222 AC自动机 模板
- [模板]-AC自动机
- ac自动机模板
- HDU 2222 Keywords Search(我的第一道AC自动机,模板题)
- HDOJ2222Keywords Search【AC自动机模板题】
- 【AC自动机模板】(转自木子日匀大神)
- AC自动机 ( 动态建树模板 )——Keywords Search ( HDU 2222 )
- AC自动机模板 hdoj2222 UVA-11468
- hdu 3065 病毒侵袭持续中 AC自动机模板题 ,,一A。
- Keywords Search---hdu2222(AC自动机 模板)
- luogu P3796【模板】AC自动机(加强版)
- AC自动机 模板 hdu 2222