bzoj2938poi2000病毒

Posted paul-guderian

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了bzoj2938poi2000病毒相关的知识,希望对你有一定的参考价值。

技术分享图片

  • 题解:

    •  对病毒串建立ac自动机;
    • 有一个无限长的串等价于可以一直在自动机上匹配,等价于自动机上的转移有环;
    • 当然前提是去掉病毒节点的fail子树;
    • 写一个dfs记录是否在栈中,来过没有找到就不必再来了再记录一个vis保证复杂度;
    • 然而。。。。。。我在找环的时候呆了很久,最后写了tarjan;
    • 如果你也是有些tarjan的危险想法的话注意特判转移的自环的情况;
    • 技术分享图片
       1 #include<bits/stdc++.h>
       2 using namespace std;
       3 const int N=30010;
       4 int n,sz,ch[N][2],fl[N],que[N],head,tail,vis[N],hd[N],o,dfn[N],idx,low[N],fg;
       5 struct Edge{int v,nt;}E[N<<1];
       6 char s[N];
       7 void get_fl(){
       8     for(int i=0;i<2;i++)q[++tail]=ch[u][i],adde(0,ch[u][i]);
       9     while(head<tail){
      10         int u=que[++head];
      11         for(int i=0;i<2;i++){
      12             int&v=ch[u][i];
      13             if(!v){v=ch[fl[u]][i];continue;}
      14             fl[v]=ch[fl[u]][i];
      15             if(!vis[v])adde(v,ch[v][i]),adde(v,fl[v][i]);
      16         }
      17     }
      18 }
      19 void tarjan(int u){
      20     if(fg)return ;
      21     que[++head]=u;
      22     dfn[u]=low[u]=++idx;
      23     for(int i=hd[u];~i;i=E[i].nt){
      24         int v=E[i].v;
      25         if(!dfn[v])tarjan(v),low[u]=min(low[u],low[v]);
      26         else if(!del[v])low[u]=min(low[u],dfn[v]);
      27     }
      28     if(dfn[u]==low[u]){
      29         int cnt=0;
      30         do{
      31             int v=que[head--];
      32             cnt++;
      33         }while(v!=u);
      34         if(cnt > 1)fg=1;
      35     }
      36 }
      37 int main(){
      38     freopen("bzoj2938.in","r",stdin);
      39     freopen("bzoj2938.out","w",stdout);
      40     scanf("%d",&n);
      41     for(int i=1;i<=n;i++){
      42         scanf("%s",s+1);
      43         int len=strlen(s+1),u=0;
      44         for(int j=1;j<=len;j++){
      45             if(!ch[u][s[j]-0])ch[u][s[j]-0]=++sz;
      46             u=ch[u][s[j]-0];
      47         }
      48         vis[u]=1;
      49     }
      50     head=0;
      51     get_fl();
      52     tarjan(0);
      53     if(fg)puts("TAK");else puts("NIE";)
      54     return 0;
      55 }
      bzoj2938

       

以上是关于bzoj2938poi2000病毒的主要内容,如果未能解决你的问题,请参考以下文章

BZOJ2938 [Poi2000]病毒 AC自动机

BZOJ2938: [Poi2000]病毒

[bzoj 2938] [Poi2000]病毒]

bzoj2938poi2000病毒

2938: [Poi2000]病毒

2938. [POI2000]病毒AC自动机