1.堆排序
1.1 构建最大堆
1.2 堆排序
1.3 代码及注释
//堆排序,时间复杂度为O(nlogn)
//堆排序中的堆指的是最大堆
#include<iostream>
using namespace std;
//交换
void exchange(int &a,int &b){
int temp;
temp = a;
a= b;
b= temp;
}
//调整最大堆,这个函数假定以pos位置作为根节点,其左右子数都是最大堆。仅仅只有a[pos]与其两个(或者只有左孩子)孩子a[2*pos]和a[2*pos+1]的大小关系不确定。需要以pos为根,自上而下的递归调整
void Max_Heapify(int *a,int pos,int len){ //这里的len的作用,在构建最大堆时为原数组的大小10,由于堆排序是原址排序,已排序好的放在数组最后,因此数组的待排序长度需要递减
int l= 2*pos;
int r= 2*pos+1;
int largest = pos;
if((l<=len)&&(a[l]>a[pos])){
largest = l;
}
if((r<=len)&&(a[r]>a[largest])){
largest = r;
}
if(largest!=pos){
exchange(a[pos],a[largest]);
Max_Heapify(a,largest,len);
}
}
//建立最大堆,从第一个非叶节点开始直到根节点
void Build_Max_Heap(int *a){
for(int i=5;i>=1;i--){
Max_Heapify(a,i,10);
}
}
//输出
void printHeap(int *a){
for(int i=1;i<=10;i++){
cout<<a[i]<<" ";
}
cout<<endl;
}
//堆排序海曙,首先建立堆,每次把最大堆的根节点与待排序的最后一个元素做交换,待排序的长度递减,这样同时也会破坏最大堆,所以每次还需要从根节点开始调整最大堆
void Heap_Sort(int *a){
Build_Max_Heap(a);//首先要建立最大堆
exchange(a[1],a[10]);
for(int i=9;i>1;i--){ //循环n-2次
Max_Heapify(a,1,i);
exchange(a[1],a[i]);
}
printHeap(a);
}
//主函数
int main(){
int array[] = {0,4,1,3,2,16,9,10,14,8,7}; //待排序数组,这个数组的0号元素不存放数据,不参与排序,目的是为了满足节点与其子节点的下标对应关系
// (若一个节点下标为pos,则2*pos为其左孩子,2*pos+1为它的右孩子,pos/2为它的父节点)
Heap_Sort(array);
system("pause");
return 0;
}
1.4 结果