用于查找最长重复子字符串的算法公式如下
1)build the suffix tree
2)find the deepest internal node with at least k leaf children
但我无法理解为什么这样可行,所以基本上是什么使这个算法正确?另外,我发现这个算法的源代码是找到的在O(n)中重复的子串,其中n是子串的长度,这对我来说也不清楚!让我们考虑下面的树,这里最长的重复子串是“ru”,如果我们应用DFS它会找到它5步但不是2步
你能解释一下这些东西吗?
感谢
答案 0 :(得分:0)
我想你完全知道O(n)(Big O表示法)指的是 n 的某个数量的增长顺序,而不是 n 数量等于 n 我写这个是因为读了我怀疑的问题...... 我把它写成一个aswer而不是评论,因为评论有点太长了(我想......)
答案 1 :(得分:0)
给定 N 字符的字符串 S ,构建相应的后缀树是 O(N)(使用诸如{{的算法3}})。
现在,这样的后缀树可以有Ukkonen's(包括root和leaves)。
如果您遍历树并计算从给定节点可到达的叶子数量及其深度,您将找到所需的结果。为此,您从根开始并探索每个孩子。
一些伪代码:
traverse(node, depth):
nb_leaves <-- 0
if empty(children(node)):
nb_leaves <-- 1
else:
for child in children(node):
nb_leaves <-- nb_leaves + traverse(child, depth+1)
node.setdepth(depth)
node.setoccurrences(nb_leaves)
return nb_leaves
初始通话为traverse(root, 0)
。由于结构是树,因此每个节点只能调用traverse
。这意味着对traverse
的最大呼叫数为 2N - 1 ,因此整体遍历仅为 O(N)。现在,您只需跟踪具有最大深度的节点,并通过添加相关的簿记机制来验证:depth > 0 && nb_leaves >= k
。这并不妨碍整体复杂性。
最后,找到这样一个子串的算法的复杂性是 O(N)其中 N 是输入字符串的长度(而不是长度)匹配的子串!)。
注意:上面描述的遍历基本上是后缀树上的DFS。