堆排序是基于二叉堆实现的,时间复杂度为O(nlogn)。
堆排序的算法步骤为:1 把无序数组构建成二叉堆。需要从小到大排序,则构建成最大堆;需要从大到小排序则构建成最小堆。2 循环删除堆顶元素,替换到二叉堆的末尾,调整堆产生新的堆顶。
public class HeapSort {
public static void main(String[] args) {
HeapSort heapSort = new HeapSort();
int[] array = {1, 3, 2, 6, 5, 7, 8, 9, 10, 0};
heapSort.heapSort(array);
System.out.println(Arrays.toString(array));
}
private void heapSort(int[] array) {
//步骤1:时间复杂度为O(n),数组构建二叉堆,从小到大排序,此处构造为最大堆
for (int i = (array.length - 2) / 2; i >= 0; i--) {
downAdjust(array, i, array.length);
}
System.out.println(Arrays.toString(array));
//步骤2:时间复杂度为O(nlogn)
for (int i = array.length - 1; i > 0; i--) {
//交换第一个元素和最后一个元素的值
int temp = array[i];
array[i] = array[0];
array[0] = temp;
//注意此处的数组长度为i,每调整一次,下一次的长度减少1
downAdjust(array, 0, i);
}
}
private void downAdjust(int[] array, int parentIndex, int length) {
int childIndex = 2 * parentIndex + 1;
int temp = array[parentIndex];
while (childIndex < length) {
if (childIndex + 1 < length && array[childIndex] < array[childIndex + 1]) {
childIndex++;
}
if (temp >= array[childIndex]) {
break;
}
array[parentIndex] = array[childIndex];
parentIndex = childIndex;
childIndex = 2 * parentIndex + 1;
}
array[parentIndex] = temp;
}
}