找到AVL树中两个数字之间的最小间隙

时间:2012-09-08 12:10:44

标签: search data-structures tree avl-tree

我有一个数据结构作业,除了常规的AVL树函数之外,我还要添加一个函数,它返回AVL树中任意两个数字之间的最小间隙(AVL中的节点实际上代表数字。)

假设我们在AVL树中有数字(作为节点)1 5 12 20 23 21,该函数应该返回任意两个数字之间的最小间隙。在这种情况下它应该返回“1”,即| 20-21 |或| 21-20 |。

应该在O(1)中完成。

试图思考很多,我知道有一个伎俩但是找不到它,我花了好几个小时。

还有另一项任务是找到最大间隙,这很容易,它是最小和最大数之间的差异。

2 个答案:

答案 0 :(得分:6)

您需要扩展数据结构,否则您无法获得组成树的数字之间的最小间隙的O(1)搜索。

你有额外的约束,不会增加插入/删除/搜索功能的时间复杂度,我认为你也不想增加空间复杂性。

考虑一个通用节点 r ,左子树 r.L 和右子树 r.R ;我们将扩展节点 r 附加数字 r.x 中的信息,定义为:

之间的最小值
  • (仅当r.L不为空时)r值和r.L上最右边叶子的值
  • (仅当r.L深于1时)r.L根节点的x值
  • (仅当r.R不为空时)r值和r.R上最左边叶子的值
  • (仅当r.R深于1时)r.R根节点的x值

(如果以前的条件都没有,则为未定义,如果是叶节点)

此外,为了快速插入/删除,我们需要在每个内部节点中添加对其最左侧和最右侧叶节点的引用。

您可以通过以下添加内容看到:

  • 空间复杂度仅以常数因子增加
  • 插入/删除函数需要更新x值以及每个已更改子树的根的最左边和最右边的叶子,但是以一种不需要超过O(log(n))的方式实现
  • 树根的x值是函数需要返回的值,因此可以在O(1)中实现它

树中的最小间隙是根节点的 x 值,更具体地说,对于每个子树,子树元素中的最小间隙只是子树根 x 价值。

此声明的证明可以通过递归来完成: 让我们考虑一个以节点 r 为根的树,左子树 r.L 和右子树 r.R 。 归纳假设是 r.L r.R x 值的根是子树的节点值之间的最小间隙的值。 很明显,只考虑值排序列表中具有相邻值的节点对,可以找到最小间隙;由 rL 节点存储的值形成的对在 rL x 值中具有最小间隙,考虑到右边也是如此子树。鉴于( r.L 中的任何节点值)< L 根节点的值< ( r.R 中的任何节点值),唯一不考虑的相邻值对是两个:

  1. 由根节点值和较高 r.L 节点值组成的对
  2. 由根节点值和较低 r.R 节点值组成的对
  3. 具有较高值的​​ r.L 节点是AVL树属性的最右边的叶子,具有较低值的 r.R 节点是其最左边的叶子。 分配给 rx 值时,四个值之间的最小值(rL根x值,rR根x值,(r -rL根)间隙,(r -rR根)间隙)与分配相同整个树中连续节点值之间的较小间隙,相当于任何可能的节点值对之间的较小间隙。 子树中的一个或两个为空的情况是微不足道的。 只有一个或三个节点组成的树的基本情况,看到树根的x值是最小间隙值是微不足道的。

答案 1 :(得分:0)

此功能可能对您有所帮助:

int getMinGap(Node N)
    {
        int a = Integer.MAX_VALUE ,b = Integer.MAX_VALUE,c = Integer.MAX_VALUE,d = Integer.MAX_VALUE;
        if(N.left != null) {
            a = N.left.minGap;
            c = N.key - N.left.max;
        }

        if(N.right != null) {
            b = N.right.minGap;
            d = N.right.min - N.key;
        }

        int minGap = min(a,min(b,min(c,d)));

        return minGap;
    }

这是节点数据结构:

class Node
{
    int key, height, num, sum, min, max, minGap;
    Node left, right;

    Node(int d)
    {
        key = d;
        height = 1;
        num = 1;
        sum = d;
        min = d;
        max = d;
        minGap = Integer.MAX_VALUE;
    }
}