【问题标题】:Avl tree- find first key missing from the tree after iAvl 树 - 在 i 之后找到树中丢失的第一个键
【发布时间】:2019-04-02 13:19:45
【问题描述】:

我有上述问题,我正在努力解决。 Avl 树也有每个节点的子树大小,我知道最大值。我需要找到不在树中的i 之后的下一个第一个数字。我需要在O(logn) 时间完成。

我来了

if i bigger/equal the maximum then return i+1,

我尝试在其他情况下找到树中i 之后的最小值,我知道如果我找到的数字大于i+1 return i+1,我可以在O(logn) 中做到这一点。

现在我知道如果i+1 在树中,我需要继续搜索,但我得到的时间复杂度比我需要的要大。 非常感谢任何指导。我不是在寻找代码,只是在指定时间内如何解决它的想法或指导

【问题讨论】:

  • 有人吗?非常感谢您的帮助
  • 有人吗?非常感谢您的帮助
  • 我了解您可能不是以英语为母语的人(我也不是),但您的问题很难阅读,请尝试使其更具可读性。它可能有助于标记格式以区分数学符号和纯文本。

标签: data-structures computer-science


【解决方案1】:

作为提示,考虑一下如果您将元素放在数组中而不是 AVL 树中,您将如何解决这个问题。你将如何使用修改后的二分搜索在时间 O(log n) 中解决这个问题?

一旦你弄清楚如何做到这一点,看看你是否可以调整你的解决方案以在二叉搜索树而不是数组中工作。直觉将非常相似,只是不是查看每个点的整个元素范围的中间,而是查看当前子树的根,虽然靠近中间,但并不总是完全正确在中间。

【讨论】:

    【解决方案2】:

    我认为您的问题可能更多在于时间复杂度分析而不是实际算法。

    我们知道,如果处理得当,在高度为log[2](n) 的结构良好的 AVL 树中搜索的时间将始终为log[2](n)。在这种情况下搜索丢失的项目与搜索现有项目没有什么不同。

    假设您有一个 AVL 树 A,它包括 ii+1。那么我们知道i+1要么是i的父节点,而i是左子节点,要么i+1i的右子节点。所以我们可以得出结论:

    if i ^ i+1 in A => i+1(l)=i v i(r)=i+1

    所以如果你找到i 并且它的父节点不是i+1 它的右子节点必须是i+1。您可以在找到 i+1 后将其扩展到 i=i+1 并继续检查此情况。这里很酷的是,如果您跟踪遍历过的节点,那么在i 之后的每个值i+n 只需要查看一个位置。

    如果你通过[i+7, i+4, i]你马上知道如果A包含i它不能包含i+1。这是由于i+1 < i+4i < i+1 < i+4

    如果你通过[i-6, i-2, i] 你也马上知道如果A 包含i+1 它不能包含i+1。这是由于i-2 < i+1i-2 < i < i+1

    如果你要通过[i+7, i+3, i+1, i],你会发现ii+1,因为i+3不是i+2,你知道i+2必须是i+1的右子节点,因为它必须不是i+3 的孩子,因为它更小,但i+1 已经占据了左孩子的位置。所以你检查i+1的右孩子是否是i+2,你继续从i+3开始检查i+4,本质上是使用算法:

    define stack //use your favourite stack implementaion
    let n = root node
    let i = yourval
    while n.val != i
         stack.push(n)
         if i > n.val
             n = n.right
         else //equivalent to "else if i < n.val" since loop condition ensures they are not equal
             n = n.left
    
    while !stack.empty
        if stack.peek.right.val != queue.peek.val + 1
            //Implies parent holds value
            temp = stack.pop.val + 1
            if(temp != stack.peek.val) //If the parent does not hold the next value return it
                return temp;
        else //Right child holds value
             stack.push(queue.peek.right)
             i = stack.peek.val
    return i+1 //if the stack is empty eventually return the next value
    

    由于 AVL 树的形成方式,您的堆栈最多将是 2*logn[2](n) 元素大(如果 i 是 LHS 上的叶子,最后一个值是 RHS 上的叶子)。因此,总的来说,您的搜索将使用 log[2](n) 进行初始搜索 i 和另一个 2*log[2](n) 组合,从而生成 3*log[2](n),在 Big Omicron 中仍然是 O(log[2](n))

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-12-06
      • 2018-03-31
      • 2022-01-16
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多