树形选择排序

【算法描述】
树形选择排序也叫锦标赛排序,我们可以类比比赛过程。有n个待排序的元素,把它们两两一组进行比较,取出较小的,然后在这n/2个较小者中再两两一组进行比较,取出较小的,重复上述步骤,直到取出最小元素。
这个过程用一棵满二叉树表示,在选出最小关元素后,将这个元素对应的叶子节点的值置为∞,然后把不为∞的兄弟节点移到父节点的位置。一直重复这个过程就可以了
这里写图片描述

【算法实现】

public class Sort {
    /* 对a[]按升序排列 */
    public static void treeSelectSort(int[] a) {
        int len = a.length;// 数组长度
        int nodeSize = len * 2 - 1; // 对一个满二叉树,节点总数 = 叶子节点数*2-1
        int[] tree = new int[nodeSize + 1]; // 这里将用数组表示二叉树的存储结构
        /* 填充叶子节点 */
        for (int i = len - 1, j = 0; i >= 0; i--, j++) {
            tree[nodeSize - j] = a[i];
        }
        /* 填充其他节点 */
        for (int i = nodeSize - len; i > 0; i--) {
            tree[i] = tree[i * 2] < tree[i * 2 + 1] ? tree[i * 2] : tree[i * 2 + 1];
        }
        /* 将每次找出的最小元素移走 */
        int index = 0;// 数组a的索引
        int minIndex = 0;// 最小值的索引
        while (index < len) {
            int min = tree[1]; // 这是tree的根节点,也是最小元素
            a[index++] = tree[1]; // 将tree中最小的元素取到a[0]中
            minIndex = nodeSize;
            /* 从最后的叶子节点开始,直到找到最小值的索引 */
            while (tree[minIndex] != min) {
                minIndex--;
            }
            tree[minIndex] = Integer.MAX_VALUE; // 将这个最小元素置为最大
            /* 如果这个节点还有父节点,那么就将它的兄弟节点升到父亲节点位置 */
            while (minIndex > 1) {// 根结点的索引是1
                if (minIndex % 2 == 0) {// 这个节点是左节点
                    tree[minIndex / 2] = tree[minIndex] < tree[minIndex + 1] ? tree[minIndex] : tree[minIndex + 1];
                    minIndex = minIndex / 2;
                } else {// 这个节点是右节点
                    tree[minIndex / 2] = tree[minIndex] < tree[minIndex - 1] ? tree[minIndex] : tree[minIndex - 1];
                    minIndex = minIndex / 2;
                }
            }
        }

    }/* treeSelectSort */

    public static void main(String[] args) {
        int[] a = { 12, 34, 23, 38, 65, 97, 76, 13 };
        Sort.treeSelectSort(a);
        for (int i : a) {
            System.out.print(i + "  ");
        }
    }
}

【算法分析】
含有n个叶子节点的完全二叉树的深度为h=[log2n][log2n]+1,因此在树形选择排序中,每选出一个最小元素需要进行[log2n][log2n]次比较(在h深度元素比较一次,在h-1深度比较一次,到h-2深度比较,直到根节点),移动元素的次数小于等于比较次数,所以算法的时间复杂度为O(nlog2nO(nlog2n)。与简单选择排序算法相比,降低了比较次数的数量级,增加了n-1个额外的存储空间存放中间比较结果。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值