如果我的订单统计二进制平衡树有find(x)
个不同的整数作为其键,我想编写函数 x
,它返回不在的最小整数树,大于O(log(n))
。在6,7,8,10,11,13,14
时间。
例如,如果树中的键是find(6)=9
,那么find(8)=9
,find(10)=12
,find(13)=15
,max
。
我考虑在O(log(n))
中找到x
,在i_x
中找到O(log(n))
(标记为i_x=n-(m-x)
)的索引,然后max+1
我可以简单地返回6,7,8,10,11,13,14
。
索引我的意思是在“
中,索引6为0,索引10为3,例如......
但我在其他案件中遇到麻烦......
答案 0 :(得分:2)
根据wikipedia,订单统计树在log(n)时间内支持这两项操作:
首先获得x的等级,然后选择x的高级等级,直到找到插入缺失元素的位置。但这有最坏情况的n * log(n)。
相反,一旦你获得了x的等级,你就会进行一种二分搜索。基本思想是树中的数字x和y之间是否存在空格。如果rank(x) - rank(y) != x - y
,则会有一个空格。
一般情况是:当搜索区间中的数字[lo,hi](lo和hi是树中的等级,mid是中间等级),如果lo和mid之间有空格则在内部搜索[ lo,mid],否则在[mid,hi]内搜索。 你最终会找到你寻找的号码。
但是,此解决方案不会在log(n)时间内运行,而是在log ^ 2(n)中运行。这是我能想到的最佳解决方案。
编辑:
嗯,这是一个棘手的问题,我多次改变主意。以下是我提出的建议:
我假设左节点保持较低值,右节点保持优值
find(x)
的直觉:从根目录开始,沿着树几乎,就像在标准二叉树中一样。如果我们要去的分支不包含find(x)
的解决方案,则将其删除。
我们将首先介绍基本案例:
x在左子树中的情况比较棘手,因为它可能包含x,x + 1,x + 2,x + 3等,直到y-1,其中y是存储在当前节点中的值。在这种情况下,我们希望在右子树中搜索y + 1。
但是,如果从x到y的所有数字都不在左子树中(也就是说,存在间隙),那么我们将在其中找到一个值,因此我们查看x的左子树。
问题是:如何查找子树中是否存在从x到y的序列?
python中的算法如下所示:
def find(node, x):
if node == null:
return x
if node.data < x:
return find(node.right, x)
if node.data == x:
return find(node.right, x+1)
if is_full(...):
return find(node.right, node.data+1)
return find(node.left, x)
要获得严格大于x的最小值(不在树中),第一个调用是find(root, x+1)
。如果您希望最大值大于或等于不在树中的x,则第一个调用为find(root, x)
。
is_full
方法检查左子树是否包含从x到node.data-1的所有数字。
现在,以此为出发点,我相信您可以自己找到合适的解决方案,使用每个子树中包含的节点数存储在子树根中的事实。
答案 1 :(得分:1)
我遇到了类似的问题。
找到大于x
的内容没有任何限制,只需找到BST
中缺少的元素。
以下是我的答案,完全有可能在O(lg(n))
时间内这样做,假设树几乎是平衡的。您可能需要考虑随机构建的BST
的预期高度为lg(n)
给定n
元素的证明。我使用更简单的表示法O(h)
,其中h =树的高度,所以现在有两件事是分开的。
假设和/或要求: