#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <string.h>
//堆排序
//堆是什么?能二叉树每个结点对应到数组下标的数据结构
//1234567
//最后一个父节点的数字下标 n/2-1;左孩子是 2*dad+1,即n-1;
typedef int ElemType;
typedef struct{
ElemType *elem;
int TableLen;
}SSTable;
void ST_Init(SSTable &ST,int len){
ST.TableLen=len;
ST.elem=(ElemType*) calloc(ST.TableLen,sizeof (ElemType));
srand(time(NULL));
for (int i = 0; i < len; ++i) {
ST.elem[i]=rand()%100;
}
}
void ST_print(SSTable ST){
for (int i = 0; i < ST.TableLen; ++i) {
printf("%d ",ST.elem[i]);
}
printf("\n");
}
void swap(ElemType &a,ElemType &b){
ElemType tmp;
tmp=a;
a=b;
b=tmp;;
}
//把某个子树调整为大根堆
void AdjustDown1(ElemType A[],int k,int len){
int dad=k; //父亲下标
int son=2*dad+1; //左孩子下标
while(son<len){
//如果左孩子小于右孩子
if(son+1<len&&A[son]<A[son+1]){ //son+1<len 避免son访问越界
son++;//拿右孩子和父亲比
}
if(A[son]>A[dad]){//右孩子和父亲比较
swap(A[son],A[dad]);
dad=son; //将孩子重新变成父节点
son=2*dad+1;//新的父亲结点的左节点
} else{
break;
}
}
}
//堆排不用递归
void HeapSort1(ElemType A[],int len){
//把堆调整为大根堆
for (int i = len/2-1; i >=0 ; --i) {//从最后一个树调整到根结点
AdjustDown1(A,i,len);
}
swap(A[0],A[len-1]);
for (int i = len-1; i >1 ; --i) {//代表剩余无序数组长度
AdjustDown1(A,0,i);//调整剩余元素变为大根堆
swap(A[0],A[i-1]);
}
//将第一个结点替换为
}
int main() {
SSTable ST;
ST_Init(ST,10);
ElemType A[10] = { 3, 87, 2, 93, 78, 56, 61, 38, 12,40};
// memcpy(ST.elem,A,sizeof(A));
ST_print(ST);
// 王道书零号元素不参与排序,但零号元素又没什么用,考研考的都是零号元素要参与排序
//王道书上比较落后,不建议采纳
// HeapSort(ST.elem, 9);
HeapSort1(ST.elem,10);//所有元素参与排序
ST_print(ST);
return 0;
}
02-04
1708
08-09
779
02-23
7515
03-23
233
07-31
470
07-21
826
03-31
121
02-11
6225