堆结构
1)堆结构就是用数组实现的完全二叉树结构
2)完全二叉树中如果每棵子树的最大值都在顶部就是大根堆
3)完全二叉树中如果每棵子树的最小值都在顶部就是小根堆
4)堆结构的heaplnsert与heapify操作
5)堆结构的增大和减少
6)优先级队列结构,就是堆结构.
i(i下标从0开始,根节点)的左孩子在数组中2i+1位置上,右孩子在2i+2位置上,i的父节点在(i-1)/2取整位置。(完全二叉树)
大根堆:每棵子树的根节点最大
小根堆:每棵子树的根节点最小
package com.algorithm;
public class Heap01 {
public static class MyMaxHeap {
private int[] heap;
private int limit;
private int heapSize;//堆中元素的长度,已经收集了多少元素
private MyMaxHeap(int limit) {
heap = new int[limit];//数组实现堆
this.limit = limit;
heapSize = 0;
}
public boolean isEmpty() {
return heapSize == 0;
}
public boolean isFull() {
return heapSize == limit;
}
//建立大根堆,每次加入一个数,使完全二叉树保持大根堆
public void push(int value) {
if (heapSize == limit) {
throw new RuntimeException("heap is full");
}
heap[heapSize] = value;//每次把新元素放到堆尾,与父节点作比较,上浮到合适位置
//value放在heapsize位置上
heapInsert(heap, heapSize++);
}
//index位置上是我刚放在堆尾的元素
private void heapInsert(int[] arr, int index) {
//停:arr[index]不比arr[index父]大了
// 停:index已经到0位置了,堆顶部
while (arr[index] > arr[(index - 1) / 2]) {
//该节点比父父节点大
swap(arr, index, (index - 1) / 2);
index = (index - 1) / 2;//上冒
}
}
//冒出最大元素,调整剩余元素仍为大根堆
//用户此时,让你返回最大值,并且在大根堆中,把最大值删掉
//剩下的数,依然保持大根堆
public int pop() {
int ans = heap[0];
swap(heap, 0, --heapSize);//堆的大小减一
heapify(heap, 0, heapSize);