堆排序
来源:互联网 发布:员工网络 访客网络 编辑:程序博客网 时间:2024/05/16 12:18
堆定义
n个关键字序列Kl,K2,…,Kn,满足如下堆性质:ki<=k(2i)且ki<=k(2i+1)(1≤i≤ n),这是小根堆,大根堆则换成>=号。//k(i)相当于二叉树的非叶结点,K(2i)则是左孩子,k(2i+1)是右孩子若将此序列所存储的向量R[1..n]看做是一棵完全二叉树的存储结构,则堆实质上是满足如下性质的完全二叉树:完全二叉树中任一非叶结点的关键字均不大于(或不小于)其左右孩子(若存在)结点的关键字。
大根堆排序的基本思想
① 初始化堆。将初始文件R[1..n]建成一个大根堆,此堆为初始的无序区
② 将关键字最大的记录R[1](即堆顶)和无序区的最后一个记录R[n]交换,由此得到新的无序区R[1..n-1]和有序区R[n],且满足R[1..n-1].keys≤R[n].key
③重建堆。由于交换后新的根R[1]可能违反堆性质,故应将当前无序区R[1..n-1]调整为堆。然后再次将R[1..n-1]中关键字最大的记录R[1]和该区间的最后一个记录R[n-1]交换,由此得到新的无序区R[1..n-2]和有序区R[n-1..n],且仍满足关系R[1..n-2].keys≤R[n-1..n].keys,同样要将R[1..n-2]调整为堆。
……
直到无序区只有一个元素为止。
重建堆
条件:R[low]的左、右子树(若存在)均已是堆。
这两棵子树的根R[2low]和R[2low+1]分别是各自子树中关键字最大的结点。若R[low].key不小于这两个孩子结点的关键字,则R[low]未违反堆[性质,以R[low]为根的树已是堆,无须调整;否则必须将R[low]和它的两个孩子结点中关键字较大者进行交换,即R[low]与R[large](R[large].key=max(R[2low].key,R[2low+1].key))交换。交换后又可能使结点R[large]违反堆性质,同样由于该结点的两棵子树(若存在)仍然是堆,故可重复上述的调整过程,对以R[large]为根的树进行调整。此过程直至当前被调整的结点已满足性质,或者该结点已是叶子为止。
初始化堆
条件:R[1...n]是随机的。显然只有一个结点的树是堆,而在完全二叉树中,所有序号大于n/2的结点都是叶子,因此以这些结点为根的子树均已是堆。这样,我们只需依次将以序号为n/2,…,1的结点作为根的子树都调整为堆即可。
C++实现
- 堆及堆排序
- 堆/堆排序特点
- 【二叉堆、堆排序】
- 二叉堆 & 堆排序
- 二叉堆 & 堆排序
- 堆与堆排序
- 堆与堆排序
- 堆与堆排序
- 堆与堆排序
- 堆与堆排序
- 堆与堆排序
- 堆和堆排序
- 堆排序(最大堆)
- 堆和堆排序
- 堆和堆排序
- 堆及堆排序
- 堆和堆排序
- 堆与堆排序
- 李彦宏:如何做一个好的产品经理
- 九度OJ 题目1472:求两个多项式的和
- 教五年内买车买房——理财篇
- 百度地图SDK for Android【Demo Place详情页】
- Telephone Country Codes
- 堆排序
- [跳槽|注意事项]职场转弯处请掌好方向盘
- Iterator与ListIterator有什么区别?
- 传智播客成都java培训中心2月25日就业班新开班
- 创建守护进程
- ARGB和PARGB
- 软件测试用例的有效性分析及评估方法
- 简单的参数注入
- linux c 生成 bitmap