红色的数表示数对应的下标
从下标为 4 的位置开始过滤结果为:
从下标为 3 的位置开始过滤,由于 7>1, 7>5,所以不需要过滤
然后从下标为 2 的位置开始过滤(过滤两次):因为要保证下面所有数均满足最大堆的定义
过滤第1次: 再过滤一次:
从下标为 1 的位置继续过滤:由于过滤 1 次后 满足8>6, 6>4,6>3,4>2,均满足最大堆定义,不需要再过滤,得
最大堆序列为:8 6 7 4 3 1 5 2
#include<stdio.h>
#include<stdlib.h>
typedef struct HNode{
int *Data; //指向存储元素的数组的指针
int Size; // 堆当前元素个数
int Capacity; //堆容量
}MaxHeap;
//PercDown(H,i)函数对父下面的所有孩子调整,始终保证该父以及所有孩子满足最大堆
void PercDown(MaxHeap* H, int p){
int Parent, Child;
int X;
X=H->Data[p];
//循环把大的数过滤上来
for(Parent=p; Parent*2<=H->Size; Parent=Child){
Child=Parent*2; //Child为左孩子下标
if((Child!=H->Size)&&(H->Data[Child]<H->Data[Child+1])) Child++; //如果Child!=H->Size而且左孩子 < 右孩子,就把 Child++变成右孩子
if(X>=H->Data[Child]) break;
else H->Data[Parent]=H->Data[Child];
}
//循环把大的数过滤上来后,把一开始的父的值赋值给孩子H->Data[Parent]
H->Data[Parent]=X;
}
//遍历父,找到父下标,调用 PercDown(H,i)函数
void BuildHeap(MaxHeap *H){
int i;
for(i=H->Size/2; i>0; i--)
PercDown(H,i);
}
int main(){
int MaxSize,i;
MaxHeap *H=(MaxHeap*)malloc(sizeof(MaxHeap));
printf("请输入数字个数:");
scanf("%d", &MaxSize);
int a[MaxSize+1];
printf("\n请输入需要建最大堆的数字:");
for(i=1;i<=MaxSize;i++)
scanf("%d",&a[i]);
H->Data=a;
H->Size=MaxSize;
H->Capacity=MaxSize;
BuildHeap(H);
printf("调整为最大堆后 层序遍历抽象出来的二叉树 的序列为:(注意:二叉树不存在,只是用数组下标表示出二叉树父子关系):\n\n");
for(i=1;i<=MaxSize;i++)
printf("%d ", H->Data[i]);
}