模板—trie图

做了某题之后发现trie的AC自动机太垃圾了,动不动就TLE,然后我就去学了trie图。

#include<iostream>
#include<cstdio>
using namespace std;
struct trie
{
    int count;
    trie *fail,*nxt[26];
    trie()
    {
        count=0;
        fail=NULL;
        for(int i=0;i<26;i++)nxt[i]=NULL;
    }
}*q[1000000],*root=new trie();
int head,tail;
char keyword[1000000],str[1000000];

void insert(char s[],trie *root)
{
    int i=0,index;
    trie *p=root;
    while(s[i])
    {
        index=s[i]-‘a‘;
        if(p->nxt[index]==NULL)p->nxt[index]=new trie();
        p=p->nxt[index];
        i++;
    }
    p->count++;
}
void build_ac(trie *root)
{
    q[++tail]=root;
    while(head!=tail)
    {
        trie *p=q[++head];
        for(int i=0;i<26;i++)
        if(p->nxt[i]!=NULL)
        {
            if(p==root)p->nxt[i]->fail=p;
            else       p->nxt[i]->fail=p->fail->nxt[i];
            q[++tail]=p->nxt[i];
        }
        else
        {
            if(p==root)p->nxt[i]=p;
            else       p->nxt[i]=p->fail->nxt[i];
        }
    }
}
int ask(trie *root)
{
    trie *p=root;
    int i=0,index,cnt=0;
    while(str[i])
    {
        index=str[i]-‘a‘;
        p=p->nxt[index];
        trie *temp=p;
        while(temp!=root && temp->count!=-1)
            cnt+=temp->count,temp->count=-1,temp=temp->fail;
        i++;
    }
    return cnt;
}
signed main()
{
    int n,T;
    trie *p;
    cin>>T;
    while(T--)
    {
        p=new trie();
        cin>>n;
        for(int i=1;i<=n;i++)
        {
            cin>>keyword;
            insert(keyword,p);
        }
        cin>>str;
        build_ac(p);
        cout<<ask(p)<<endl;
    }
}

原文地址:https://www.cnblogs.com/Al-Ca/p/11025281.html

时间: 2024-10-03 20:29:19

模板—trie图的相关文章

Trie图(模板)

Trie图(蒟蒻听说AC自动机能做的题Trie图都能做,而且AC自动机可能被卡,就没学过AC自动机),最近想捡一捡,好久之前做的了. Trie图,就是一个在Trie树上建的图  大概描述一下 比如说有几个字符串: abc abcd bcd bacd jdr ac 先把它们存在Trie树中: 就像KMP那样,做出这样的逻辑判断: bacd比较到第三位bac结果没有d,但起码bac有了,所以以bac为前缀的或以bac后缀为前缀的串是不用再比较前缀了. 所以出现了fail指针,为失配情况重新定位方案.

Trie图

DFA 确定性有限状态自动机 DFA确定性有限状态自动机是一种图结构的数据结构,可以由(Q, q0, A, Sigma, Delta)来描述,其中Q为状态集,q0为初始状态,A为终态集合,Sigma为字母表,Delta为转移函数.它表示从唯一一个起始状态q0开始,经过有限步的Delta转移,转移是根据字母表Sigma中的元素来进行,最终到达终态集合A中的某个状态的状态移动.  如图所示是一个终态集合为{"nano"}的DFA.     DFA只能有一个起点而可以有多个终点.每个节点都有

hihoCoder #1036 : Trie图 (AC自动机)

#1036 : Trie图 时间限制:20000ms 单点时限:1000ms 内存限制:512MB 描述 前情回顾 上回说到,小Hi和小Ho接受到了河蟹先生伟大而光荣的任务:河蟹先生将要给与他们一篇从互联网上收集来的文章,和一本厚厚的河蟹词典,而他们要做的是判断这篇文章中是否存在那些属于河蟹词典中的词语. 当时,小Hi和小Ho的水平还是十分有限,他们只能够想到:"枚举每一个单词,然后枚举文章中可能的起始位置,然后进行匹配,看能否成功."这样非常朴素的想法,但是这样的算法时间复杂度是相当

Trie图/AC自动机

made...发财谷题解基本是Trie图... 我永远喜欢AC自动机.jpg 下面是P3808 [模板]AC自动机(简单版) 的两种写法 Trie图 const int MAXN = 1000010; int t[MAXN][26], word[MAXN], fail[MAXN], cnt, q[MAXN]; inline void insert(char *s) { int u = 0; for (int i = 1; s[i]; ++i) { int v = s[i] - 'a'; int

DNA Sequence POJ - 2778 邻接矩阵 trie图 矩阵快速幂

首先构造trie图. 我们明确一点的是,给出trie图,那么所有点的转移方式都是唯一可以确定的.即使是没有这个字符,他也会指向根节点. 我们根据离散数学的知识可以知道.计算有向图的邻接矩阵,然后k次方,就能够计算出从某一个点到另一个点,有多少条长度为k的路径. 故,我们构造出来trie图,拿出该图的邻接矩阵,就能计算路径数目.--(注意改图是有向图)-- trie图的构造不说了,模板. 邻接矩阵的构造根据trie图来的.我们在trie图上找到每一个节点,查看他的相邻节点,即A,G,C,T四个点指

hiho一下 第二周&amp;第四周:从Trie树到Trie图

hihocoder #1014 题目地址:http://hihocoder.com/problemset/problem/1014 hihocoder #1036 题目地址: http://hihocoder.com/problemset/problem/1036 trie图其实就是trie树+KMP #1014trie树 #include<stdio.h> #include <algorithm> #include <cstring> #include <str

Trie图 &amp; AC自动机初学(1)

题目来源于:Hihocoder 时间限制:20000ms 单点时限:1000ms 内存限制:512MB 描述 前情回顾 上回说到,小Hi和小Ho接受到了河蟹先生伟大而光荣的任务:河蟹先生将要给与他们一篇从互联网上收集来的文章,和一本厚厚的河蟹词典,而他们要做的是判断这篇文章中是否存在那些属于河蟹词典中的词语. 当时,小Hi和小Ho的水平还是十分有限,他们只能够想到:"枚举每一个单词,然后枚举文章中可能的起始位置,然后进行匹配,看能否成功."这样非常朴素的想法,但是这样的算法时间复杂度是

hihoCoder#1036 Trie图

原题地址 看了这篇博文,总算是把Trie图弄明白了 Runtime Error了无数次,一直不知道为什么,于是写了个脚本生成了一组大数据,发现果然段错误了. 调试了一下午,总算闹明白了,为什么呢? 1. 空间超大的变量不要放在函数里,会爆栈,应该弄成全局变量或者是从堆上动态分配. 2. 看清题目的数据范围,一开始我的MAX_NODE设的是1024... 代码: 1 #include <iostream> 2 #include <cstring> 3 4 using namespac

hdu2457 Trie图+dp

hdu2457 给定n个模式串, 和一个文本串 问如果修改最少的字符串使得文本串不包含模式串, 输出最少的次数,如果不能修改成功,则输出-1 dp[i][j] 表示长度为i的字符串, 到达状态j(Trie图中的结点)所需要修改的最少次数 那么dp[0->n][0->size] = INF ,  dp[0][root] = 0,  n代表字符串长度, size代表状态数 那么答案就是  min{dp[n][size]} 我们根据模式串所建的Trie图, 进行模拟构造不包含模式串的字符串 从第一个