一步一步学算法-堆排序
来源:互联网 发布:windows虚拟内存转移 编辑:程序博客网 时间:2024/05/23 23:02
二叉堆有两种:最大堆和最小堆。在最大堆中,最大堆的特性是指除了根以外的每个节点 i,有
A[PARENT(i)] >= A[i]
即某个节点的值至多是和其父节点的值一样大。这样,堆中的最大元素就存放在根节点中;并且,在以某一节点为根的子树中,各节点的值都不大于该子树根节点的值。最小堆则相反。这里以最大堆为例子。
实现堆排序分为三个部分,即三个函数:
- 保持堆的性质
- 建堆
- 堆排序算法
保持堆的性质
void Algorithm::maxHeapify(int a[], int length, int i){ int largest = i; int left = 2 * i + 1; // left child int right = 2 * i + 2; // right child // compare with two child node and get largest node if (left < length && a[left] > a[largest]) { largest = left; } if (right < length && a[right] > a[largest]) { largest = right; } if (largest != i) { int tmp = a[largest]; a[largest] = a[i]; a[i] = tmp; maxHeapify(a, length, largest); }}
该函数的作用是调整二叉树,使得以 i 为根节点的子树成为最大堆。
建堆
void Algorithm::buildMaxHeap(int a[], int length){ for (int i = (length - 2) / 2; i >= 0; --i) { maxHeapify(a, length, i); }}
建堆的过程就是把数组 a 自底向上用 maxHeapify 函数变成一个最大堆。
堆排序算法
void Algorithm::heapSort(int a[], int length){ buildMaxHeap(a, length); for (int i = length - 1; i >= 1; --i) { // 交换a[0]和a[i] int tmp = a[i]; a[i] = a[0]; a[0] = tmp; maxHeapify(a, i, 0); }}
通过堆的性质可以知道最大堆的根节点值一定最大,所以数组中最大元素在根 a[0],通过把它与 a[n] 互换来达到最终的位置。由于互换后 a[0] 的值被改变了,违背了最大堆的性质,这时调用 maxHeapify 调整数组前 n-1 个元素可以保持这一性质。
测试结果:
0 0
- 一步一步学算法-堆排序
- 一步一步写算法--堆排序
- 一步一步写算法(之堆排序)
- 一步一步写算法(之堆排序)
- 一步一步解析java排序算法--堆排序(最小堆)
- 一步一步解析java排序算法---堆排序(最大堆)
- 菜鸟学算法-----堆排序
- 每天学一点算法-堆排序算法
- 一步一步复习数据结构和算法基础-堆排序
- <菜鸟学算法-A排序(分治的思想:堆排序)>
- 二哥学算法之快速排序和堆排序
- 小菜学堆排序
- 菜鸟学算法之--堆排序
- 排序算法--堆排序
- 排序算法-堆排序
- 排序算法---堆排序
- 【排序算法】堆排序
- 排序算法-堆排序
- drools入门(二)
- 计算机图书
- 父子控制器的开发准则
- Python:函数参数传递:传值?引用?
- Java语言语法2
- 一步一步学算法-堆排序
- nyoj 38 布线问题(kruskal 最小生成树)
- 创建自己的Sprite子类时需要做哪些工作?
- hdu 5438 Ponds(线段树+dfs)
- 浏览器解析过程
- 二叉树的创建和遍历
- HDU 5233 杂题
- JSP之POST与GET的区别
- 排序算法 golang 实现