KMP、扩展KMP、Tire树(字典树)与AC自动机学习小记(填坑ing)

KMP


扩展KMP


Tire树


哇我居然不会Tire树

啊啦Tire树,便是字典树(单词查找树),又叫前缀树,是一种树形结构,是哈希树的变种
实际上上面那句话没个屁用

  • 其实发明Tire的人还是很逗的

  • 它的发明者叫它“tree”,但我们都叫它“try”

  • 于是它就变成了“try”

在讲Tire树之前,先YY想象一下
先想像一下我们在查英语字典的时候,比如查“dynamic”这个单词
我们会先查以d开头的词条,接着查y,继续到n,直到查到“dynamic”为止
而毋庸置疑我们并不会真的把字典翻个遍查阅每一个单词直到查到为止

so,Tire也差不多是这思想吧……


看看长相再说

下面便是一棵好看的 Tire

在这棵Tire中,一共存了6个单词:apple、and、append、antiy、banana和band

这个就不必多说了吧……真心水……


没有什么性质和优点怎么行呢

仔细咀嚼咀嚼下面的东东……?随意随意

Tire的三条性质

  • 根节点不包含字符,除根节点外每一个节点都只包含一个字符
  • 从根节点到某一节点,路径上经过的字符连接起来,为该节点对应的字符串
  • 每个节点的所有子节点包含的字符都不相同

明显地,在Tire里查找一个字符串的时间复杂度 O ( l e n )
若Tire的根节点到当前节点所表示的字符串存在,那么就在这个节点打个标记就好

Tire的若干优点

  • 之所以叫Tire前缀树,是因为它把多个字符串的公共前缀放在了一起,节省空间
  • Tire限制了字符串的查找方向,减少无用的比较时间,时间上比哈希树优很多
  • Tire树实用的还有是能查询某个字符串的前缀是否出现过,而hash很难(除非浪费大量多余空间)做到

其实Tire就大概那个样多说无益
以前一直卡着我打不出来Tire的原因是我不会建Tire树……(too naive)


建Tire


AC自动机


还是不知道AC自动机是个什么

第一次看见“AC自动机”以为是用来黑掉OJ的自动AC的神妙机器……尴尬……

咳咳AC自动机,全称Aho-Corasick automaton,该算法在1975年产生于贝尔实验室,是著名的多模匹配算法
当然上面那段来自度娘的话仍然没个屁用

  • 单模匹配就是给你一个单词、一个字符串,问你这个单词是否在这个字符串中出现过

  • 当然用KMP可以很好很快速地解决这个问题

那么多模匹配是什么?

  • 多模匹配就是给出很多个单词和一个字符串,问你有多少个单词在这个字符串中出现过

  • 明显多个KMP暴力做GG

  • 这时就要用到AC自动机


我把AC自动机叫做Tire2.0

AC自动机是一个非常玄妙、神奇、高深莫测的算法,但却不难

其实和LCT splay + 树剖差不多,AC自动机 KMP + Tire
它是建立在Tire的基础上的,而核心思想就是多了一个fail失配指针来实现多模匹配

其实上面说了也没用不会AC自动机不贴图说得再详细也没用


无图无真相

请务必仔仔细细阅读以下内容否则AC自动机你就学不会了

  • fail指针指向的到底是啥子?

  • 每个节点的fail失配指针指向的是以当前节点表示的字符为最后一个字符的最长当前字符串的后缀字符串的最后一个节点

您要是能像绕口令般把上面那句话背下来我就服气

还是看一张图片容易理解毕竟本人蒟蒻鼠绘还是辣鸡

此Tire中有四个单词:ABCD、ABD、CD、BCE

对于Tire中的 x 点,为什么它的 f a i l 指向 y 点呢?
根节点到 x 节点表示的字符串为“ABC”,而在Tire中它的存在的最长后缀是“BC”
所以 x 节点便指向“BC”最后一个字符表示的节点——就是 y

至于 y 点的 f a i l 指向 z 点也就不难理解啦
在Tire中存在的“BC”的最长后缀为“C”,于是 y f a i l 便指向了代表“C”的 z

Ain’t that easy?!Ain’t that funny???


猜你喜欢

转载自blog.csdn.net/enjoy_pascal/article/details/79100904