字符串考前总结

复习字符串

  • KMP
  • AC自动机
  • manacher
  • SA
  • SAM

AC自动机

Fail树

  • 祖先是后代节点对应字符串的后缀

给模式串建AC自动机,文本串中模式串出现次数:走到的每个节点fail祖先单词结尾个数;模式串在文本串中出现次数:文本串走的时候cnt++,子树cnt和。

  • 队列中就是拓扑序

DP

  • 考虑一边生成字符串,一边在AC自动机上走,\(f[i][j]\)表示生成了i位(字符串前i位)自动机上走到j
  • 考虑trie图上的转移 建出图来 矩乘/图的性质

题目

  1. 1212: [HNOI2004]L语言

    f[i]表示\(S[1,i]\)是否能表示出来,走到每个节点用到祖先的单词结尾转移

  2. 3172: [Tjoi2013]单词

    文本串就是模式串,插入时cnt++

  3. 套路DP

  4. 2434: [Noi2011]阿狸的打字机

    结合题目的性质,一边模拟一边生成字符串,一个字符串结束后统一处理他的询问。fail树的dfs序。

  5. 添加新文本串,询问某个模式串在多少种文本串里出现过

    模式串建AC自动机,考虑添加一个文本串,走到的节点记录下来求树链的并


后缀数组

sa是后缀排序后的结果

rnk是每个后缀的名次

height是第i名与第i-1名的LCP

如果只用到求LCP之类的直接写SA比写SAM方便一点吧

常用技巧

  1. 差分 注意长度变化

  2. 按Height大小把sa分组

  3. 枚举长度L,\(S_{1+i*L}\)设为关键点。每个长为L的子串覆盖且仅覆盖一个关键点,统计数量可以利用(最长延伸L-1)

  4. 两个字符串拼起来,用#隔开;自身反转拼起来

  5. 单调栈:称为最小值的区间 / 套个set,任意位置删除+二分查找

  6. ST表

  7. 并查集:满足r-1成立时r也成立,枚举LCP长度,从大到小合并

题目

  1. 可重叠的k次最长重复子串

    二分最长长度,sa分组同一组height>=mid

  2. 重复次数最多的连续重复子串

    枚举L,计算每两个关键点向前向后能匹配多长

  3. ABA(\(|B|\)已知)形式的子串有多少个

    枚举\(|A|=L\),每个关键点i和i+B+L向前后匹配,最长L-1

  4. LCS

    直接上SAM / 拼起来,求height两个不在同一串的最大值

  5. 不重叠最长重复子串

    二分+分组 / 并查集 , 核心都是看sa的最大差值


后缀自动机

Right集合

  • SAM中的一个状态s表示了一个Right−equivalence class,也就是所有Right集合=Right(s)的子串,长度[Min(s), Max(s)]

  • 基数排序后递推,所有的np初始化为1(主链上的初始化为1) 同样可以递推最左/右位置

    最后right=1的状态,出现位置就是Max(s)

Parent Tree

  • Parent树祖先Right集合大,字符串长度(路径长度)短
  • Parent祖先对应字符串集合是后代的后缀
  • Max(fa)=Min(s)−1
  • 反转字符串的后缀树,\(LCS \rightarrow LCP\)

性质

  • 从init开始走转移边可以得到所有子串
  • 出现向父亲(Parent边)传递,接收串数从儿子(仍然Parent边)获取

广义后缀自动机

  • 把很多串的SAM建到了一个SAM上,建每个串的时候都从root开始(last=root)
  • 广义后缀自动机是Trie树的后缀自动机,可以解决多主串问题
  • 直接给Trie建GSAM,边dfs边建其他地方不变,会产生多余节点不过没关系

题目

  1. 最小循环表示 / 最小后缀(加一个最小的字符在最后)

  2. LCS (注意走suffix link后更新当前长度t[u].val)

  3. 多个串LCS 每个的最大,多个的最小 注意向父亲传递,后代出现祖先一定可以取Max,拓扑逆序更新

  4. 字典序k小子串

  5. LCT维护Parent-Tree

  6. 两个串统计CS个数 一定注意后代出现,父亲也出现了并且可以取最大

  7. 建出后缀树 树形DP

  8. 每个状态出现在不同子串的次数 GSAM 跑字符串,更新sl父亲,cur=当前串就停下

    统计一个串出现次数,除了经过的状态,还要统计经过状态的Parent祖先

  9. 和SA一样注意配合DP思想,不要总想直接做

  10. 周期同构:复制一遍贴在后面(最后一个字符可以不贴)

走的时候保证长度为n:这一步走完后Min(s)>=n时走par

posted @ 2017-04-05 23:05  Candy?  阅读(626)  评论(0编辑  收藏  举报