zoukankan      html  css  js  c++  java
  • UvalLive4670(AC自动机模板)

    放上刘汝佳的模板:

      1 #include <cstdio>
      2 #include <cstring>
      3 #include <string>
      4 #include <algorithm>
      5 #include <queue>
      6 #include <map>
      7 using namespace std;
      8 
      9 const int maxnod = 150 * 70 + 100;
     10 
     11 int n;
     12 char str[155][75], T[1000005];
     13 map<string, int> mp;
     14 
     15 struct AC_Automata {
     16     int ch[maxnod][26];//Trie树转移
     17     int cnt[155];//每个子串出现了几次
     18     int val[maxnod];//某节点是否为子串结尾以及是哪个串的结尾
     19     int f[maxnod];//失配,转移到别的树枝继续找
     20     int last[maxnod];//找到了后缀相同的其他可行子串
     21     int sz;
     22 
     23     void init() {
     24         sz = 1;
     25         mp.clear();//与ac自动机无关
     26         memset(ch[0], 0, sizeof ch[0]);
     27         memset(cnt, 0, sizeof cnt);
     28     }
     29 
     30     int idx(char c) { return c - 'a'; }
     31 
     32     void insert(char* s, int v) {//Trie树的插入
     33         int u = 0, n =strlen(s);
     34         for (int i = 0; i < n; ++i) {
     35             int c = idx(s[i]);
     36             if (!ch[u][c]) {
     37                 memset(ch[sz], 0, sizeof ch[sz]);
     38                 val[sz] = 0;
     39                 ch[u][c] = sz++;
     40             }
     41             u = ch[u][c];
     42         }
     43         val[u] = v;
     44     }
     45 
     46     void getfail() {
     47         queue<int> Q;
     48         f[0] = 0;
     49         for (int i = 0; i < 26; i++) {
     50             int u = ch[0][i];
     51             if (u) {
     52                 f[u] = last[u] = 0;
     53                 Q.push(u);
     54             }
     55         }
     56         while (!Q.empty()) {
     57             int r = Q.front(); Q.pop();
     58             for (int c = 0; c < 26; c++) {
     59                 int u = ch[r][c];
     60                 if (!u)    continue;
     61                 Q.push(u);
     62                 int v = f[r];
     63                 while (v && !ch[v][c])    v = f[v];//当前这个不行看看别人行不行
     64                 f[u] = ch[v][c];
     65                 last[u] = val[f[u]] ? f[u] : last[f[u]];
     66             }
     67         }
     68     }
     69 
     70     void Success(int j) {
     71         if (j) {
     72             cnt[val[j]]++;
     73             Success(last[j]);
     74         }
     75     }
     76 
     77     void find(char* T) {
     78         int n = strlen(T);
     79         for (int i = 0, j = 0; i < n; ++i) {
     80             int c = idx(T[i]);
     81             while (j && !ch[j][c])    j = f[j];
     82             j = ch[j][c];
     83             if (val[j])    Success(j);
     84             else if (last[j])    Success(last[j]);
     85         }
     86     }
     87 }ac;
     88 
     89 int main() {
     90     while (~scanf("%d", &n) && n) {
     91         ac.init();
     92         for (int i = 1; i <= n; i++) {
     93             scanf("%s", str[i]);
     94             ac.insert(str[i], i);
     95             mp[str[i]] = i;
     96         }
     97         ac.getfail();
     98         scanf("%s", T);
     99         ac.find(T);
    100 
    101         int ans = -1;
    102         for (int i = 1; i <= n; i++) {
    103             ans = max(ans, ac.cnt[i]);
    104         }
    105         printf("%d
    ", ans);
    106         for (int i = 1; i <= n; i++) {
    107             if (ac.cnt[mp[str[i]]] == ans)    puts(str[i]);
    108         }
    109     }
    110     return 0;
    111 }
  • 相关阅读:
    [POJ 1050]To the Max
    P1678 烦恼的高考志愿
    P1873 砍树
    P1102 A-B 数对
    P6771 [USACO05MAR]Space Elevator 太空电梯
    P2347 砝码称重
    P1832 A+B Problem(再升级)
    P1679 神奇的四次方数
    P1877 [HAOI2012]音量调节
    P1049 装箱问题
  • 原文地址:https://www.cnblogs.com/AlphaWA/p/10597028.html
Copyright © 2011-2022 走看看