模板——AC自动机

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <cstring>
 4 #include <queue>
 5 #include <algorithm>
 6 using namespace std;
 7 
 8 const int maxnode = 10000;
 9 const int _size = 26;
10 
11 struct ACauto {
12     int ch[maxnode][_size];
13     int val[maxnode];
14     int f[maxnode];
15     int last_[maxnode];
16     int sz;
17     ACauto() {
18         sz = 1;
19         memset(ch[0], 0, sizeof (ch[0]));
20     }
21     int idx(int c) {return c - 'a';}
22     
23     void insert(char *s, int v) {   //插入字符串s和权值v
24         int u = 0, n = strlen(s);
25         for(int i = 0; i < n; i++) {
26             int c = idx(s[i]);
27             if(!ch[u][c]) {
28                 memset(ch[sz], 0, sizeof (ch[sz]));
29                 val[sz] = 0;
30                 ch[u][c] = sz++;
31             }
32             u = ch[u][c];
33         }
34         val[u] = v;
35     }
36     void clear() {
37         sz = 1;
38         memset(val, 0 , sizeof val);
39         memset(ch[0], 0, sizeof (ch[0]));
40         memset(f, 0, sizeof f);
41         memset(last_, 0, sizeof last_);
42     }
43     //计算失配函数
44     void getfail() {
45         queue<int> q;
46         for(int c = 0; c < _size; c++) {
47             int u = ch[0][c];
48             if(u) {
49                 q.push(u);
50                 f[u] = 0;
51                 last_[u] = 0;
52             }
53         }
54         while(!q.empty()) {
55             int r = q.front(); q.pop();
56             for(int c = 0; c < _size; c++) {
57                 int u = ch[r][c];
58                 if(!u) {
59                     ch[r][c] = ch[f[r]][c];
60                     continue;
61                 }
62                 q.push(u);
63                 int v = f[r];
64                 while(v && !ch[v][c]) v = f[v];
65                 f[u] = ch[v][c];
66                 last_[u] = val[f[u]] ? f[u] : last_[f[u]];
67             }
68         }
69     }
70     //打印以j结尾的所有模板串序号
71     void print(int i,int j) {
72         if(j) {
73             printf("%d : %d\n", i, val[j]);
74             print(i,last_[j]);
75         }
76     }
77     //在文本串中找模板
78     void find(char* T) {
79         int n = strlen(T);
80         int j = 0;
81         for(int i = 0; i < n; i++) {
82             int c = idx(T[i]);
83             j = ch[j][c];
84             if(val[j]) print(i, j);
85             else if(last_[j]) print(i, last_[j]);
86         }
87     }
88 };

 

posted @ 2016-11-11 15:40  kiraa  阅读(134)  评论(0编辑  收藏  举报