📜  合并排序树以获取范围顺序统计信息(1)

📅  最后修改于: 2023-12-03 15:22:57.717000             🧑  作者: Mango

合并排序树以获取范围顺序统计信息

排序树是一种有序的数据结构,其中每个节点都包含一个值,使得左子节点上的值小于父节点上的值,而右子节点上的值大于父节点上的值。排序树中最常用的一种是二叉搜索树(BST)。类似于BST,合并排序树(MST)是一种有序树,其中每个节点都可以包含多个元素,而在每个节点中存储的元素是按顺序排列的。 M ST通过在排序树中添加两个重要操作来扩展标准BST:分割操作和合并操作。

分割操作

给定一个MST T和一个元素x,分割操作将M ST T划分为三个M ST,分别包含小于,等于和大于x的元素。这可以通过对T进行拆分和重构来实现。

public static void split(MergeSortTree T, Comparable x, MergeSortTree[] leftTree, 
                          MergeSortTree[] eqTree, MergeSortTree[] rightTree) {
        if (T == null) {
            MergeSortTree[] emptySet = { null };
            leftTree[0] = emptySet[0];
            eqTree[0] = emptySet[0];
            rightTree[0] = emptySet[0];
        }
        else {
            int cmp = T.min().compareTo(x);
            if (cmp > 0) {
                split(T.left, x, leftTree, eqTree, new MergeSortTree[] { T });
                rightTree[0] = T.right;
            }
            else if (cmp < 0) {
                split(T.right, x, new MergeSortTree[] { T }, eqTree, rightTree);
                leftTree[0] = T.left;
            }
            else    // T.min() == x 
            {
                MergeSortTreeNode[] emptySet = { null };
                eqTree[0] = new MergeSortTree(new MergeSortTreeNode(x, emptySet[0]));
                leftTree[0] = T.left;
                rightTree[0] = T.right;
            }
        }
    }

从代码中可以看出,如果x小于当前节点中的最小值,则递归地分割左子树;如果x大于当前节点中的最小值,则递归地分割右子树。不幸的是,并非所有节点都包含x。如果x不在树中,则需要subclassMIT一个MST,其中eqTree是一棵只包含元素x的树。

合并操作

给定两个 MS T T1和 T2,合并操作将它们合并为一个新的M ST T。这可以通过查找它们的最小值并将它们的“左”和“右”子树相应地递归到下一个级别来实现。

public static MergeSortTree meld(MergeSortTree T1, MergeSortTree T2) {
        if (T1 == null) {
            return T2;
        }
        if (T2 == null) {
            return T1;
        }
        if (T1.min().compareTo(T2.min()) <= 0) {
            MergeSortTreeNode[] emptySet = { null };
            MergeSortTree[] rightTree = { null };
            split(T2, T1.min(), new MergeSortTree[] { null }, 
                  new MergeSortTree[] { null }, rightTree);
            return new MergeSortTree(new MergeSortTreeNode(T1.min(), 
                  new MergeSortTree[] { T1.left, rightTree[0] }));
        }
        else {
            return meld(T2, T1);
        }
    }

从代码中可以看出,如果T1为空,则返回T2;如果T2为空,则返回T1。然后,它比较T1的最小值和T2的最小值,将它们分为两个组:小于或等于T1的最小值的所有元素放在它的左子树中,而大于T1的最小值的所有元素放在其右子树中。然后,递归地调用融合来合并子树。