Java实现排序算法之堆排序

一、综述

       堆排序是选择排序中的一种,算法复杂度是O(nlogn),最坏最好都是这个。下面用Java实现一个堆排序,并用注释的方式解释了堆排序的思想和原理。

 

二、Java实现堆排序

 

import java.util.*;


public class Solution {
    
    public int[] MySort (int[] arr) {
        // 1. 根据adjustHeap的定义,先建立堆,需要从底层往上构建
        for(int i = arr.length/2 - 1; i >= 0; i--){
            adjustHeap(arr, i, arr.length);
        }
        
        // 2. 开始排序,每次交互堆顶元素到最后去,再把剩余元素调整为堆
        for(int j = arr.length - 1; j > 0; j--){
            swap(arr, 0, j);
            adjustHeap(arr, 0, j);
        }
        return arr;
    }
    
    /**
    * 调整堆,建立在大頂堆已经构建的基础上,此时i指向的元素不是最大的
    * 需要逐层往下移动它,比较它的左右孩子,找到最大的节点和父节点替换
    * 替换过后,子堆有可能不满足条件,需要递归调整
    */
    public void adjustHeap(int[] arr, int i, int length){
        if(arr == null || arr.length == 0) return;
        int parent = arr[i];
        Integer left = 2 * i + 1 >= length ? null : arr[2 * i + 1];
        Integer right = 2 * i + 2 >= length ? null : arr[2 * i + 2];
        if(null == left && null == right) return;
        
        int curMaxIndex = i;
        
        if(right == null){
            if(left != null && left > parent){
                curMaxIndex = 2 * i + 1;
            }
        }
        //注意有右孩子,必然有左孩子,因为堆是完全二叉树
        if(right != null){
            if(left >= right && left > parent){
                curMaxIndex = 2 * i + 1;
            }else if(right >= left && right > parent){
                curMaxIndex = 2 * i + 2;
            }
        }
        if(curMaxIndex != i){
            swap(arr, i, curMaxIndex);
            //交换过后,递归调整子堆
            adjustHeap(arr, curMaxIndex, length);
        }
        
        
    }
    
    private void swap(int[] a, int i,int j){
        int temp = a[i];
        a[i] = a[j];
        a[j] = temp;
    }
}

 

 

 

三、结果检验

 

public class maintest {

	public static void main(String[] args) {

		int[] a = { 45, 6, 43, 78, 12, 90, 23, 21, 41, 64, 31, 91, 81, 6 };

		AHeapSort.HeapSort(a, a.length);

		for (int e : a) {
			System.out.print(e + "  ");

		}

	}
}

//调用输出结果为:6  6  12  21  23  31  41  43  45  64  78  81  90  91

 

 

 

  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值