AC自动机

 

study from :https://pan.baidu.com/s/1Igr_1EgL5FtB-zpRKosToQ (别人的ppt,如有侵权,请告知我)

 

没必要初始化

如果所有的变量初始值为0/NULL

如果是多组数据,每次根节点和辅助节点重新创建!

 

fail 长度比之间小

指针 很多个链组成,一个节点,只指向有且只有一个节点;而一个节点,有可能被多个节点指向。同时也是拓扑结构。

 

每次bfs搜索:最大代码 点数*26('a'-'z') 链式结构

可以利用之前的搜索结果

 

 

 

 

https://www.luogu.org/problemnew/show/P3808

  1 /*
  2 模式串出现的总次数
  3 */
  4 #include <cstdio>
  5 #include <cstdlib>
  6 #include <cmath>
  7 #include <cstring>
  8 #include <string>
  9 #include <algorithm>
 10 #include <iostream>
 11 using namespace std;
 12 #define ll long long
 13 
 14 const double eps=1e-8;
 15 const ll inf=1e9;
 16 const ll mod=1e9+7;
 17 const int maxn=1e6+10;
 18 
 19 struct node
 20 {
 21     int g,cond;
 22     node *nex[26],*fail,*pre;
 23 }*tr,*be,*p,*pos,*td;
 24 
 25 node *q[maxn];
 26 char str[maxn];
 27 
 28 int main()
 29 {
 30     int n,len,i,head,tail,d,sum=0;
 31     tr=new node();
 32     be=new node();
 33     tr->pre=be;
 34     tr->fail=be;
 35     be->fail=be;
 36     for (i=0;i<26;i++)
 37         be->nex[i]=tr;
 38 
 39     scanf("%d",&n);
 40     while (n--)
 41     {
 42         scanf("%s",str);
 43         pos=tr;
 44         len=strlen(str);
 45         for (i=0;i<len;i++)
 46         {
 47             d=str[i]-97;
 48             if (!pos->nex[d])
 49             {
 50                 p=new node();
 51                 pos->nex[d]=p;
 52                 p->pre=pos;
 53             }
 54             pos=pos->nex[d];
 55         }
 56         pos->g++;
 57     }
 58 
 59     head=0,tail=1;
 60     q[1]=tr;
 61     while (head<tail)
 62     {
 63         head++;
 64         td=q[head];
 65         for (i=0;i<26;i++)
 66             if (td->nex[i])
 67             {
 68                 q[++tail]=td->nex[i];
 69                 pos=td->fail;
 70                 while (!pos->nex[i])
 71                     pos=pos->fail;
 72                 td->nex[i]->fail=pos->nex[i];
 73             }
 74     }
 75 
 76     scanf("%s",str);
 77     len=strlen(str);
 78     pos=tr;
 79     for (i=0;i<len;i++)
 80     {
 81         d=str[i]-97;
 82         while (!pos->nex[d])
 83             pos=pos->fail;
 84         pos=pos->nex[d];
 85 
 86         p=pos;
 87         while (!p->cond)
 88         {
 89             sum+=p->g;
 90             p->cond=1;
 91             p=p->fail;
 92         }
 93     }
 94     printf("%d",sum);
 95     return 0;
 96 }
 97 /*
 98 2
 99 b
100 a
101 abcd
102 
103 2
104 ab
105 ac
106 abc
107 
108 2
109 ababc
110 abc
111 ababc
112 
113 3
114 ab
115 abc
116 abca
117 ababc
118 
119 6
120 ab
121 abc
122 abc
123 abc
124 abab
125 ababc
126 ababc
127 */

 

https://www.luogu.org/problemnew/show/P3796

  1 /*
  2 一个模式串出现的最大次数
  3 */
  4 #include <cstdio>
  5 #include <cstdlib>
  6 #include <cmath>
  7 #include <cstring>
  8 #include <string>
  9 #include <algorithm>
 10 #include <iostream>
 11 using namespace std;
 12 #define ll long long
 13 
 14 const double eps=1e-8;
 15 const ll inf=1e9;
 16 const ll mod=1e9+7;
 17 const int maxn=1e6+10;
 18 
 19 struct node
 20 {
 21 //    char c;
 22     int g,hav;
 23     node *nex[26],*pre,*fail;
 24 }*tr,*be,*p,*pos,*q[maxn],*td;
 25 
 26 int maxg=1,cnt_g,num[150+10];
 27 
 28 char str[maxn],s[150+10][70+10];
 29 
 30 int main()
 31 {
 32     int n,len,i,j,d,head,tail,N;
 33 
 34     while (1)
 35     {
 36         scanf("%d",&n);
 37         if (n==0)
 38             break;
 39 
 40         ///init
 41         tr=new node();
 42         be=new node();
 43         tr->pre=be;
 44         tr->fail=be;
 45         be->fail=be;
 46         for (i=0;i<26;i++)
 47             be->nex[i]=tr;
 48         maxg=1;
 49 
 50         for (N=1;N<=n;N++)
 51         {
 52             scanf("%s",str);
 53             strcpy(s[N],str);
 54 
 55             len=strlen(str);
 56             pos=tr;
 57             for (i=0;i<len;i++)
 58             {
 59                 d=str[i]-97;
 60                 if (!pos->nex[d])
 61                 {
 62                     p=new node();
 63                     pos->nex[d]=p;
 64                     p->pre=pos;
 65 //                    p->c=d;
 66                 }
 67                 pos=pos->nex[d];
 68             }
 69             pos->hav=N;
 70         }
 71 
 72         head=0,tail=1;
 73         q[1]=tr;
 74         while (head<tail)
 75         {
 76             head++;
 77             td=q[head];
 78             for (d=0;d<26;d++)
 79                 if (td->nex[d])
 80                 {
 81                     pos=td->fail;
 82                     while (!pos->nex[d])
 83                         pos=pos->fail;
 84                     td->nex[d]->fail=pos->nex[d];
 85                     q[++tail]=td->nex[d];
 86                 }
 87         }
 88 
 89         scanf("%s",str);
 90         len=strlen(str);
 91         pos=tr;
 92         for (i=0;i<len;i++)
 93         {
 94             d=str[i]-97;
 95             while (!pos->nex[d])
 96                 pos=pos->fail;
 97             pos=pos->nex[d];
 98             pos->g++;
 99         }
100 
101         for (i=tail;i>=1;i--)
102         {
103             pos=q[i];
104             if (pos->hav)
105             {
106                 if (maxg<=pos->g)
107                 {
108                     if (maxg<pos->g)
109                     {
110                         maxg=pos->g;
111                         cnt_g=1;
112                     }
113                     else
114                         cnt_g++;
115 
116                     num[cnt_g]=pos->hav;
117 
118 //                    j=0;
119 //                    p=pos;
120 //                    while (p!=tr)
121 //                    {
122 //                        s[cnt_g][j++]=p->c+97;
123 //                        p=p->pre;
124 //                    }
125 //                    s[cnt_g][j]=0;
126 //                    reverse(s[cnt_g],s[cnt_g]+j);
127                 }
128             }
129             pos->fail->g+=pos->g;
130         }
131 
132         sort(num+1,num+cnt_g+1);
133         printf("%d\n",maxg);
134         for (i=1;i<=cnt_g;i++)
135             printf("%s\n",s[num[i]]);
136 //            printf("%s\n",s[i]);
137 
138         ///free pointer
139     }
140     return 0;
141 }
142 /*
143 2
144 cab
145 ab
146 cabcabcab
147 */

 

posted @ 2018-08-28 16:47  congmingyige  阅读(228)  评论(0编辑  收藏  举报