1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62
| const int N = 5e4+10, M = 26;
struct ACA { int tot, ch[N][M], deep[N], fail[N]; int cnt[N];
ACA() { tot = 0; for (int i = 0;i < N;i++) memset(ch[i], 0, sizeof(int)*M); memset(deep, 0, sizeof(int)*N); memset(fail, 0, sizeof(int)*N); memset(last, 0, sizeof(int)*N); memset(cnt, 0, sizeof(int)*N); }
void insert(string& cur, int cost) { int n = cur.size(), node = 0; for (int i = 0;i < n;i++) { int c = cur[i]-'a'; if (!ch[node][c]) { ch[node][c] = ++tot; deep[tot] = i+1; } node = ch[node][c]; } cnt[node] = cost; }
void build() { queue<int> q; for (int i = 0;i < M;i++) { if (ch[0][i]) { q.push(ch[0][i]); } } while (q.size()) { int cur = q.front(); q.pop(); for (int i = 0;i < M;i++) { int nxt = ch[cur][i], nf = ch[fail[cur]][i]; if (nxt) { fail[nxt] = nf; q.push(nxt); } else { ch[cur][i] = nf; } } } } };
int query(string s) { int res = 0; for (int i = 1, root = 0;i <= n;i++) { int c = target[i-1]-'a'; root = ac.ch[root][c]; for (int j = root;j;j = ac.fail[j]) { res += ac.cnt[j]; ac.cnt[j] = 0; } } return res; }
|