heapSort

HeapSort(堆排序):

    • 二叉树,有父节点(parent)和左孩子(left),右孩子(right)

    • 堆的大小等于这个堆中有多少个元素

    • 最大堆性质:parent>=children,父节点 大于等于 两个孩子

    • 最小堆性质: children>=parent,父节点 小于等于 两个孩子

  • 下标推算

    • 叶节点(没有children的节点)的下标为(n/2)+1, (n/2)+2, ..., n, n为heap的大小

    • 根节点(heap的起始点)的下标为1时,parent位置:i,则left位置: 2i,right位置: 2i + 1

    • 根节点下标为0时,parent位置:i,则left:2i + 1, right:2i + 2

    • children位置:i,则parent位置: i / 2

  • ​​​​​​​优先队列

    • insert(S,x)在集合S中插入x
    • maximum(S)返回集合S中的最大元素
    • extract-max(S)去掉并返回S中最大元素
    • increase-key(S,x,k)把S中的x更新为k,k大于等于x
    • 应用:计算机系统的作业调动,extract-max将所有作业中优先级最高的调出执行,调度器可以用insert随时增加新的作业。heap与应用程序的链接通过句柄(handle)
    • 由于涉及到增删,Java中的array已经无法满足需求,储存元素的容器应选择其他
    • Java中提供PriorityQueue
public class heapSort {
    //heap的根节点取0


    //检查subscript作为parent时,堆是否符合最大堆性质
    //maxHeapify将三个元素:父节点,左子节点,右子节点分为一个小堆,进行一次排查
    //算法导论6.1
    public static void maxHeapify(int[] array, int subscript, int heapEnd){
        int left = subscript * 2 + 1;
        int right = subscript * 2 + 2;
        //假设父节点为最大的数字
        int largest = subscript;

        //检查左孩子是否大于最大的数字
        if (left <= heapEnd && array[left] > array[largest]){
            largest = left;
        }

        //检查右孩子是否大于最大的数字
        if (right <= heapEnd && array[right] > array[largest]){
            largest = right;
        }

        //若最大数字的下标不在父节点,则说明子节点有数字大于父节点,交换父子位置使最大堆性质成立
        //同时递归,检查交换位置后,largest为父节点的堆是否符合最大堆性质
        if (largest != subscript){
            int temp = array[subscript];
            array[subscript] = array[largest];
            array[largest] = temp;
            maxHeapify(array, largest, heapEnd);
        }
    }

    //将无序的数组转换为符合最大堆性质的heap
    //算法导论6.2
    public static void buildMaxHeap(int[] array){
        int length = array.length;
        //叶节点(无children的node)为n/2+1, n/2+2,...,n
        //此处只maxHeapify有子节点的节点,既除去叶节点外的节点
        for (int i = length / 2; i >= 0; i --){
            maxHeapify(array, i, length - 1);
        }
    }

    //将最大堆性质heap转换为从小到大排列的数组
    //算法导论6.4
    public static void heapConvert(int[] array){
        int length = array.length;
        int heapEnd = length - 1;
        //从堆中最大元素开始遍历,每次将最大元素和数组最后一个元素对调,然后将改变后的堆再维护成拥有最大堆性质的堆
        //随后再次提出最大元素,重复
        for (int i = length - 1; i >= 1; i --){
            int temp = array[i];
            array[i] = array[0];
            array[0] = temp;
            heapEnd = heapEnd - 1;
            maxHeapify(array, 0, heapEnd);
        }
    }
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值