AC日记——病毒侵袭 hdu 2896
思路:
好题;
代码:
#include <queue> #include <cstdio> #include <cstring> using namespace std; #define maxn 100001 int ne[60005][130],tag[60005],fail[60005],n,tot,m,ans; char ch[maxn]; bool vis[60005],out,sc[505]; queue<int>que; int main() { int i,j,len,now,temp; scanf("%d",&n); tot=1,ans=0;getchar(); for(i=1;i<=n;i++) { gets(ch); len=strlen(ch); now=1; for(j=0;j<len;j++) { if(!ne[now][ch[j]]) ne[now][ch[j]]=++tot; now=ne[now][ch[j]]; } tag[now]=i; } que.push(1); while(!que.empty()) { now=que.front();que.pop(); for(i=0;i<130;i++) { if(!ne[now][i]) continue; if(now==1) fail[ne[now][i]]=now; else { temp=fail[now]; while(temp) { if(ne[temp][i]) { fail[ne[now][i]]=ne[temp][i]; break; } temp=fail[temp]; } if(!temp) fail[ne[now][i]]=1; } que.push(ne[now][i]); } } scanf("%d",&m);getchar(); for(i=1;i<=m;i++) { out=false; for(j=0;j<=n;j++) sc[j]=false; for(j=0;j<60005;j++) vis[j]=false; gets(ch); len=strlen(ch),now=1; for(j=0;j<len;j++) { if(ne[now][ch[j]]) now=ne[now][ch[j]]; else { temp=fail[now]; while(temp) { if(ne[temp][ch[j]]) { now=ne[temp][ch[j]]; break; } temp=fail[temp]; } if(!temp) now=1; } temp=now; while(!vis[temp]) { vis[temp]=true; if(!sc[tag[temp]]&&tag[temp]) out=true,sc[tag[temp]]=true; temp=fail[temp]; } } if(out) { printf("web %d:",i); for(j=0;j<=n;j++) if(sc[j]) printf(" %d",j); printf("\n"),ans++; } } printf("total: %d\n",ans); return 0; }