hdu5384(AC自动机)

来源:互联网 发布:ug软件自学网 编辑:程序博客网 时间:2024/05/16 07:44

这道题是多模字符串匹配的题,需要用到AC自动机。直接套模板AC。

#include <iostream>#include <cstdio>#include <cstring>#include <cstdlib>#include <cmath>#include <algorithm>#include <queue>using namespace std;struct Trie{    int next[100002][26],fail[100002],end[100002];    int root,L;    int newnode()    {        for(int i = 0; i < 26; i++)            next[L][i] = -1;        end[L++] = 0;        return L-1;    }    void init()    {        L = 0;        root = newnode();    }    void insert(char buf[])    {        int len = strlen(buf);        int now = root;        for(int i = 0; i < len; i++)        {            if(next[now][buf[i]-'a'] == -1)                next[now][buf[i]-'a'] = newnode();            now = next[now][buf[i]-'a'];        }        end[now]++;    }    void build()    {        queue<int>Q;        fail[root] = root;        for(int i = 0; i < 26; i++)            if(next[root][i] == -1)                next[root][i] = root;            else            {                fail[next[root][i]] = root;                Q.push(next[root][i]);            }        while( !Q.empty() )        {            int now = Q.front();            Q.pop();            for(int i = 0; i < 26; i++)                if(next[now][i] == -1)                    next[now][i] = next[fail[now]][i];                else                {                    fail[next[now][i]]=next[fail[now]][i];                    Q.push(next[now][i]);                }        }    }    int query(char buf[])    {        int len = strlen(buf);        int now = root;        int res = 0;        for(int i = 0; i < len; i++)        {            now = next[now][buf[i]-'a'];            int temp = now;            while( temp != root )            {                res += end[temp];                //end[temp] = 0;    //为了避免重复计数而做的,这里不需要。                temp = fail[temp];            }        }        return res;    }};char buf[10001];Trie ac;int m;char s[100001][10002];int main(){    int T;    int n;    scanf("%d",&T);    while( T-- )    {        scanf("%d%d",&n, &m);        ac.init();        for(int i = 0; i < n; i++)        {            scanf(" %s", s[i]);        }        for(int i = 0; i < m; i++)        {            scanf("%s",buf);            ac.insert(buf);        }        ac.build();        for(int i = 0; i < n; i++)        {            printf("%d\n",ac.query(s[i]));        }    }    return 0;}


0 0
原创粉丝点击