引入

我们首先提出一个问题:
给出n个串每个串的长度≤m
然后给出一个长度为k的串,询问前n个串中有多少个是匹配成了的

暴力搜索

这题不是sb题目吗?
随随便便O(kmn)跑过。
。。。。
n=10000 m=50
k=1000000
。。。。
好吧——我们用AC自动机吧

样例

首先我们举一个例子,我们有n=3个串he 和 her 和 she
然后我们通过构建Trie可以得到下图

这里红色的节点到根的路径可以构成一个串(怎么那么像后缀自动机?)然后我们可以发现

正文

概念

我们使用Fail(i)表示i节点用虚线连接的边,这样的边我们的作用就是当前节点到根的路径构成的字符串的最长的存在的后缀的串的位置。比如she 和 he 中 he 就是 she 的最长的后缀所以我们连接 e2->e这样我们假设从e2无法再继续伸展的时候我们就可以O(1)找到类似的串,然后继续进行伸展得到如下的图

这样比如我们匹配sher的时候我们首先沿着边走到e2然后不需要重新搜索,而是选择立即跳转到e节点然后搜索到r节点

这样我们就构造出了一个AC自动机的图

构建方法

就使用上面的例子

对于这样的一个图,我们首先队列中有

Queue 0 1
h s

同时将深度为1的节点连接Fail到root

然后我们扫描一遍h节点可以得到e节点然后我们扫描s节点可以发现s的Fail边上的root节点存在和s的儿子h相同的另一个h那么因为s的fail边上的所有节点的后缀相同,所以我们有h2和h节点同时增加一个节点后仍然满足上面的Fail边的概念,所以我们h2->h得到

同时我们的队列变成了

Queue 0 1
2 h2

对于下面的伸展我们可以得到(同理):

呵呵呵代码时间:

代码

void Insert(char *s){int len = strlen(s), u = root;for(int i=0;i<len;i++){int id = idx(s[i]);if(!pool[u].ch[id]) pool[u].ch[id] = ++ecnt;u = pool[u].ch[id];}pool[u].End_Flag++;
}
void build(){queue<int> que;for(int i=0;i<26;i++)if(pool[root].ch[i])que.push(pool[root].ch[i]);int u, v, t, p;while(!que.empty()){u = que.front();que.pop();for(int i=0;i<MAXK;i++) if(pool[u].ch[i]){v = pool[u].ch[i];que.push(v);p = pool[u].Fail;while(p && !pool[p].ch[i]) p = pool[p].Fail;t = pool[p].ch[i];pool[v].Fail = t;pool[v].last = pool[t].End_Flag ? t : pool[t].last;}}
}

感谢

感谢您阅读这篇文章,如果有不足的地方请做出评论谢谢

转载于:https://www.cnblogs.com/JeremyGJY/p/5921588.html

【AC自动机】【数据结构】【树】【Aho-Corasick automation】AC自动机理解(入门)...相关推荐

  1. 【SAM套路/AC自动机+主席树】CF547E Mike and Friends

    [题目] CF 给定 n n n个串 a i a_i ai​, Q Q Q组询问 a l ∼ a r a_l\sim a_r al​∼ar​中 a x a_{x} ax​出现了多少次. ∑ ∣ a i ...

  2. TypeScript:Aho–Corasick算法实现敏感词过滤

    敏感词过滤应该是许多后端同事经常会遇到的需求,无论是评论.弹幕.文章,都需要做敏感词过滤处理来规避风险.在前端开发中,使用replace函数来替换字符串是我们的常规操作,在这之前我思考过如果用Java ...

  3. 数据结构---树(所有类型的树总结)

    文章目录 数据结构---树 1.二叉树 2.二叉查找树-BST 3.平衡二叉树-AVL 4.红黑树 5.哈夫曼树 6.B树 7.B+树 8.R树 总结 数据结构-树 本章总结数据结构中一些树的特征和结 ...

  4. 【BZOJ-13962865】识别子串字符串识别 后缀自动机/后缀树组 + 线段树

    1396: 识别子串 Time Limit: 10 Sec  Memory Limit: 162 MB Submit: 312  Solved: 193 [Submit][Status][Discus ...

  5. js 数组 实现 完全树_算法和数据结构 | 树状数组(Binary Indexed Tree)

    本文来源于力扣圈子,作者:胡小旭.点击查看原文 力扣​leetcode-cn.com 树状数组或二叉索引树(英语:Binary Indexed Tree),又以其发明者命名为 Fenwick 树.其初 ...

  6. [转]C#与数据结构--树论--平衡二叉树(AVL Tree)

    C#与数据结构--树论--平衡二叉树(AVL Tree) http://www.cnblogs.com/abatei/archive/2008/11/17/1335031.html 介绍 我们知道在二 ...

  7. 数据结构—树与二叉树

    总第119篇 前言 之前谈到的线性表.栈和队列都是一对一的数据结构,但是现实中也存在很多一对多的数据结构,这篇要写的就是一种一对多的数据结构---树.全文分为如下几部分: 树的一些基本概念 树的存储结 ...

  8. 数据结构树二叉树计算节点_查找二叉树中叶节点的数量 数据结构

    数据结构树二叉树计算节点 Algorithm: 算法: One of the popular traversal techniques to solve this kind of problems i ...

  9. 华为ac控制器web配置手册_欧姆龙AC伺服系统1S系列产品型号说明及功能介绍

    欧姆龙AC伺服系统 1S系列 提高安装调试的效率.提高设备的性能.符合国际安全标准 欧姆龙AC伺服系统 1S系列 特点 高度进化的伺服系统 缩短设备的安装调试时间.提高设备性能 从设备的设计到安装调试 ...

  10. 数据结构——树状数组

    我们今天来讲一个应用比较广泛的数据结构--树状数组 它可以在O(nlogn)的复杂度下进行单点修改区间查询,下面我会分成三个模块对树状数组进行详细的解说,分别是树状数组基本操作.树状数组区间修改单点查 ...

最新文章

  1. 第一周Access课总结
  2. 第五课.Python函数(二)
  3. (zhuan) Where can I start with Deep Learning?
  4. html jsf ajax blur,JSF和AJAX:隐藏网站的一部分,直到第一个Ajax请求
  5. vc++基于颜色直方图的图像检索,含代码
  6. C++(十)——模板(上)
  7. 疫情冬天过去,二手经济春天到来
  8. android 获取手机SD卡和手机的内部存储
  9. C语言ctype相关的几个函数
  10. python中dump函数_python中实现php的var_dump函数功能
  11. 基于SpringBoot2.x、SpringCloud和SpringCloudAlibaba的企业级微服务敏捷开发系统架构
  12. 批处理 安卓一键打包脚本快速解析
  13. Socket网络编程--简单Web服务器(3)
  14. Linux 块与文件大小
  15. AsteriskNow 实用总结
  16. Linux命令之awk:运算与判断(三)
  17. 通用权限底层研究:强大的分页功能
  18. Oracle监听器无法启动
  19. php 红包过期退回,RabbitMQ功能实现1- 红包未领取退回
  20. 【自考总结】——管理经济学(一)

热门文章

  1. java jnlp_java – 调试JNLP启动应用程序
  2. excel和python建模_利用Excel学习Python:准备篇
  3. wincc客户机打开服务器文件通讯不上,wincc客户机连不上服务器
  4. linux静默删除文件夹,Linux常用命令10 - unzip
  5. java ui自动化测试脚本,如何用Airtest编写UI自动化脚本(示例代码)
  6. 习题6-3 使用函数输出指定范围内的完数 (20 分)
  7. 160 - 40 DaNiEl-RJ.1
  8. LeetCode 454. 四数相加 II 思考分析
  9. html注释引用公共头部_HTML注释和引用
  10. 操作系统中的处理机调度调度_操作系统中的流程分类和调度