例题: Another Substring Query Problem
由于次题中模式串有重复,会影响时间复杂度,所以我们要提前处理相同的字符串。下面的方法均假设无重复模式串。并以n为模式串的总长度,m为文本串的长度。
方法一:字符串哈希 #
由于总长为n的模式串最多只有O(n)种长度,所以我们可以遍历每种长度l然后遍历每个位置i然后判断从i开始长度为l的子串是否是模式串。时间复杂度为O(nm)。
方法二:AC 自动机 #
先将所有模式串加入 AC 自动机,然后再匹配文本串。注意 AC 自动机中要维护 output link(沿 fail link 跳转时第一个模式串)。时间复杂度O(n+m+mn)。
方法三:后缀数据结构 #
后缀数据结构也能是很擅长字符串匹配的,后缀树和后缀自动机都可以解决本题,由于没学过后缀树就只写后缀自动机的做法了:
英文原文
中文翻译
注意后缀自动机是这三种做法中唯一可以在线处理询问的做法,处理单次询问的时间复杂度为O(∣s∣+occurrence),occurrence 为出现次数。整体时间复杂度O(m+n+mn)。
总结 #
三种做法各有各的优缺点,就本题来看三种做法的时间复杂度相同,时间如下:
- AC 自动机 2.55 秒(但我有一种很愚蠢的写法竟然只要 1.32 秒)
- 哈希 3.41 秒
- 后缀自动机 4.83 秒 (可能因为后缀自动机本身常数比较大)