利用大顶堆(小顶堆)的根节点记录最大数值(最小数值)的特性,可以对数值进行排序
现以大顶堆的基本思想为例:
1、将int 数组arr[1,…,n]构造为大顶堆,实现函数为heapadjust();
2、可得大顶堆的根节点,即arr[1]的数值为最大数值,然后将该值与arr[n]互换。
3、对数组arr[1,…,n-1]构造为大顶堆并将arr[1]与arr[n-1]互换,直到n-1为2停止互换,堆排序完成。
对于堆排序,最重要的两个操作就是构造大顶堆和调整堆,其实构造初始堆事实上也是调整堆的过程。
实现代码:
#include <stdio.h>
#include <stdlib.h>
//对当前节点进行调整,这样得到一个大顶堆
void heapadjust(int k[],int n)
{
int i,temp=0;
for(i=n/2;i>0;i--)
{
if(k[i]<k[2*i+1] && (2*i+1)<=n)
{
temp = k[i];
k[i] = k[2*i+1];
k[2*i+1] = temp;
}
if(k[i]<k[2*i] && 2*i<=n)
{
temp = k[i];
k[i] = k[2*i];
k[2*i] = temp;
}
}
}
//将堆排序后数组的根节点和最后一个节点的值互换
void swap(int k[],int i,int j)
{
int temp = k[i];
k[i] = k[j];
k[j] = temp;
}
//堆排序
void heapsort(int k[], int n)
{
int i =n/2;
heapadjust(k,n);
//将本次根节点的数值和最后的叶子节点互换,然后排序的数据减1,找到减一后的最大数值,再和倒数第二个节点互换
for(i=n;i>=1;i--)
{
swap(k,1,i);
heapadjust(k,i-1);
}
}
int main()
{
//堆排序,采用二叉树结构,所以下标从1开始
int arr[10]={-1,45,68,29,10,95,978,2,3,9};
heapsort(arr,9);
int i=0;
printf("排序后的结果是:\n");
for(i=1;i<10;i++)
{
printf("%d\t",arr[i]);
}
return 0;
}
结果: