堆
堆(Heap)是计算机科学中一类特殊的数据结构的统称。堆分为大根堆与小根堆。
大根堆定义:
- 大根堆是一棵完全二叉树
- 根节点的元素均大于(等于)子节点的元素。
- 任意一颗子树也均满足1和2的定义
堆的操作–以大根堆为例(基于C++语言和STL)
堆的定义(以下均分为数组定义方式和STL定义方式)
int heap[MAXN];
vector<int> heap(MAXN);
void downAdjust(int heap[], int low, int high){
// heap的index默认从1开始
// i指向父节点, j指向i的左孩子
int i = low, j = i * 2;
while(j <= high) {
// 判断子节点哪一个更大
if( j + 1 <= high && heap[j] < heap[j + 1])
j += 1;
// 向下调整堆
if(heap[i] < heap[j]) {
swap(heap[i], heap[j]); // swap需要调用algorithm文件,自己实现也可
i = j;
j = i * 2;
} else break;
}
return;
}
void make_heap(int heap[]){
for(int i = n / 2; i > 0; i--){
downAdjust(heap, i, n);
}
}
// STL版本 需要调用algorithm文件
make_heap(heap.begin(), heap.end(), less<int>()); // 大根堆
make_heap(heap.begin(), heap.end(), greater<int>()); // 小根堆
// 删除堆顶元素 放到最后去
void pop_heap(int heap[], int &n){
heap[1] = heap[n--];
downAdjust(heap, 1, n);
}
//STL版本
pop_heap(heap.begin(), heap.end());
// 堆排序
void heapSort(int heap[], int n){
createHeap(heap, n);
for(int i = n; i > 1; i--){
swap(heap[1], heap[i]);
downAdjust(heap, 1, i - 1);
}
}
//STL版本
sort_heap(heap.begin(), heap.end()); // 先要调用make_hape确定heap是一个堆
// STL的sort_heap实际是多次调用了pop_heap来实现的
// 插入元素操作
void upAdjust(int heap[], int low, int high){
// 插入元素以后向上调整堆
int i = high, j = i / 2;
while(j >= low){
if(heap[i] > heap[j]){
swap(heap[i], heap[j]);
i = j;
j = i / 2;
} else break;
}
}
void insert(int heap[], int &n, int val){
heap[++n] = val;
upAdjust(heap, 1, n);
}
// STL版本
make_heap(heap.begin(), heap.end());
heap.push_back(val);
push_heap(heap.begin(), heap.end());