假设我有一组字符串S和一个查询字符串q。我想知道S的任何成员是否是q的子串。 (出于这个问题的目的,substring包含相等,例如“foo”是“foo”的子串。)例如,假设执行我想要的函数称为anySubstring
:
S = ["foo", "baz"]
q = "foobar"
assert anySubstring(S, q) # "foo" is a substring of "foobar"
S = ["waldo", "baz"]
assert not anySubstring(S, q)
是否有任何易于实现的算法,len(S)
中的时间复杂度为子线性?如果必须首先将S处理成一些聪明的数据结构,这是可以的,因为我将使用大量q字符串查询每个S,因此这种预处理的摊销成本可能是合理的。
编辑:为了澄清,我不在乎哪个成员的S是q的子字符串,只是至少有一个是。换句话说,我只关心布尔答案。
答案 0 :(得分:13)
我认为Aho-Corasick algorithm可以满足您的需求。我认为还有另一个解决方案非常简单,它是Karp-Rabin algorithm。
答案 1 :(得分:2)
因此,如果S的长度小于潜在子串的长度之和,那么最好的选择是从S构建suffix tree然后在其中进行搜索。这相对于S的长度加上候选子串的总长度是线性的。当然,由于必须至少通过所有输入,因此不能有更复杂的算法。如果情况相反,即s的长度大于子串的总长度,那么最佳选择是aho-corasick。
希望这有帮助。
答案 2 :(得分:1)
创建正则表达式.*(S1|S2|...|Sn).*
并构建其最小DFA。
通过DFA运行您的查询字符串。