观察二叉堆的构建与调整过程
堆排序(Heap Sort)是一种利用堆数据结构设计的排序算法。它首先将数组构建成一个最大堆(父节点总是大于子节点),然后不断取出堆顶的最大元素,放到数组末尾,同时调整剩余元素重新形成堆,直到所有元素都被取出。
| 情况 | 时间复杂度 | 说明 |
|---|---|---|
| 建堆 | O(n) | 自底向上建堆的时间复杂度 |
| 排序(所有情况) | O(n log n) | 每次取出堆顶需要O(log n)调整 |
| 空间复杂度 | O(1) | 原地排序,只需常数额外空间 |
堆排序是不稳定排序,相等元素的相对顺序可能改变。
def heapify(arr, n, i): """维护最大堆性质""" largest = i left = 2 * i + 1 right = 2 * i + 2 # 左子节点更大 if left < n and arr[left] > arr[largest]: largest = left # 右子节点更大 if right < n and arr[right] > arr[largest]: largest = right # 如果最大值不是根节点,交换并继续调整 if largest != i: arr[i], arr[largest] = arr[largest], arr[i] heapify(arr, n, largest) def heap_sort(arr): """堆排序算法""" n = len(arr) # 构建最大堆(从最后一个非叶节点开始) for i in range(n // 2 - 1, -1, -1): heapify(arr, n, i) # 逐个取出堆顶元素 for i in range(n - 1, 0, -1): arr[0], arr[i] = arr[i], arr[0] # 交换堆顶和末尾 heapify(arr, i, 0) # 重新调整堆 return arr # 使用示例 arr = [12, 11, 13, 5, 6, 7] print(heap_sort(arr)) # 输出: [5, 6, 7, 11, 12, 13]
public class HeapSort { /** * 维护最大堆性质 */ private static void heapify(int[] arr, int n, int i) { int largest = i; int left = 2 * i + 1; int right = 2 * i + 2; // 左子节点更大 if (left < n && arr[left] > arr[largest]) { largest = left; } // 右子节点更大 if (right < n && arr[right] > arr[largest]) { largest = right; } // 如果最大值不是根节点 if (largest != i) { int temp = arr[i]; arr[i] = arr[largest]; arr[largest] = temp; heapify(arr, n, largest); } } /** * 堆排序算法 */ public static void heapSort(int[] arr) { int n = arr.length; // 构建最大堆 for (int i = n / 2 - 1; i >= 0; i--) { heapify(arr, n, i); } // 逐个取出堆顶元素 for (int i = n - 1; i > 0; i--) { int temp = arr[0]; arr[0] = arr[i]; arr[i] = temp; heapify(arr, i, 0); } } public static void main(String[] args) { int[] arr = {12, 11, 13, 5, 6, 7}; heapSort(arr); System.out.println(Arrays.toString(arr)); // 输出: [5, 6, 7, 11, 12, 13] } }