解题思路
- 大根堆有很好的性质,有助于升序排序
- 大根堆的根节点一定是最大的,可以用作“选择排序”,一次性选出最大的元素放到末尾
- 每次调整大根堆的时间复杂度为
O(logN)
复杂度分析
时间复杂度:O(NlogN)
空间复杂度:O(1)
是否稳定:不稳定(调整堆的过程中,需要选择交换哪个元素,导致了不稳定性)
代码
#include <vector>#include <algorithm>#include <iostream>using namespace std;// 将数组中的元素nums[i]放到大根堆中的合适位置void adjustHeap(vector<int>& nums, int i, int length) {// 先将nums[i]取出int temp = nums[i];// k用来层层遍历左右儿子节点// i用来找temp的合适的插入位置for (int k = 2 * i + 1; k < length; k = 2 * k + 1) {if (k + 1 < length && nums[k + 1] > nums[k]) {++k;}// 子节点比父节点大,说明需要向下调整if (nums[k] > temp) {nums[i] = nums[k];// 再往下找合适的插入位置i = k;} else {break;}}nums[i] = temp;}void heapSort(vector<int>& nums) {int size = nums.size();// nums[size/2-1]是第一个非叶节点for (int i = size / 2 - 1; i >= 0; --i) {adjustHeap(nums, i, size);}for (int i = size - 1; i >= 0; --i) {swap(nums[0], nums[i]);adjustHeap(nums, 0, i);}}int main(void) {vector<int> input {9,8,7,6,5,4,3,2,1};heapSort(input);for (const auto& n : input) {cout << n << " ";}return 0;}
