定义
堆是一棵完全二叉树,它大顶堆与小顶堆两类。
其中,大顶堆是指根结点比子结点均大的树。
创建
思路:
1.比较结点的左右孩子,记录较大值的下标。
2.将结点与该下标对应的值进行比较。若是孩子>结点,交换位置,否则无需调整。
3.更新记录根结点与子结点的下标
4.不断循环,直至到树底结束。
const int maxn=100;
int heap[maxn];void swap(int &a,int &b){int t;t=a; a=b; b=t;
}
//向下调整法
void downadjust(int root,int high){//hight不动,从root开始向下调整int i=root;//记录要结点下标int j=i*2;//记录子结点下标while(j<=high){if(j+1<=high && heap[j+1]>heap[j])j=j+1;//记录较大值下标if(heap[j]>heap[i]){swap(heap[i],heap[j]);//更新下标值i=j;j=i*2;}else break;//否则无需调整}
}
//建立大根堆
void create(int n){//可保证根结点是它那一堆最大的for(int i=n/2;i>=1;i--)downadjust(i,n);//向下调整
}
删除堆顶元素
void deleteNode(){heap[1]=heap[n--];//先覆盖堆顶元素,数量再减downadjust(1,n);//向下调整
}
插入
新插入的元素插入数组末尾,因此最好由下向上调整
//向上调整
void upadjust(int low,int high){//low不动,由high向上调整int i=high,j=i/2;//j为父结点while(j>=low){//保证根结点在[low,high]范围内if(heap[j]<heap[i]){swap(heap[j],heap[i]);i=j;j=i/2;//继续向上调整}else break;}
}
void insert(int value){heap[++n]=value;//插入数组后面:元素个数++,再装upadjust(1,n);
}
排序
堆排序
//将大根堆转换成小根堆
void heapSort(){create(n);//建立一个大根堆for(int i=n;i>1;i--){swap(heap[1],heap[i]);//交换根顶元素与最后一个元素downadjust(1,i-1);//此时最后一个元素是最大的,无需参与调整}
}