📅  最后修改于: 2023-12-03 14:54:56.647000             🧑  作者: Mango
在数据结构中,堆是一种特殊的树形数据结构,通常用来实现优先队列。堆有常见的两种形式:最大堆和最小堆。最大堆的性质是每个节点都大于或等于其子节点,最小堆则是每个节点都小于或等于其子节点。
问题11需要我们实现一个最小堆,其中需要包含以下几个操作:
build()
:将任意数组构建成最小堆;insert(value)
:在最小堆中插入一个元素;remove()
:删除最小堆的根节点;getMin()
:获取最小堆的根节点元素。我们可以用数组来实现一个最小堆,其中下标i的左右子节点下标分别为2i+1和2i+2,父节点下标为floor((i-1)/2)。具体实现如下:
class MinHeap {
constructor() {
this.heap = [];
}
build(arr) {
this.heap = arr;
for (let i = Math.floor(arr.length / 2) - 1; i >= 0; i--) {
this.heapifyDown(i);
}
}
insert(value) {
this.heap.push(value);
this.heapifyUp(this.heap.length - 1);
}
remove() {
if (this.heap.length === 0) {
return null;
}
if (this.heap.length === 1) {
return this.heap.pop();
}
const root = this.heap[0];
this.heap[0] = this.heap.pop();
this.heapifyDown(0);
return root;
}
getMin() {
return this.heap.length > 0 ? this.heap[0] : null;
}
heapifyUp(index) {
let parent = Math.floor((index - 1) / 2);
while (index > 0 && this.heap[index] < this.heap[parent]) {
this.swap(index, parent);
index = parent;
parent = Math.floor((index - 1) / 2);
}
}
heapifyDown(index) {
let left = 2 * index + 1;
let right = 2 * index + 2;
let smallest = index;
if (left < this.heap.length && this.heap[left] < this.heap[smallest]) {
smallest = left;
}
if (right < this.heap.length && this.heap[right] < this.heap[smallest]) {
smallest = right;
}
if (smallest !== index) {
this.swap(index, smallest);
this.heapifyDown(smallest);
}
}
swap(i, j) {
[this.heap[i], this.heap[j]] = [this.heap[j], this.heap[i]];
}
}
const minHeap = new MinHeap();
minHeap.build([4, 1, 3, 2, 16, 9, 10, 14, 8, 7]);
minHeap.insert(0);
console.log(minHeap.getMin()); // 0
console.log(minHeap.remove()); // 0
console.log(minHeap.getMin()); // 1
最小堆是一个非常有用的数据结构,它可以帮助我们高效地解决排名、选择、排序等问题。在实现最小堆时,需要注意堆化操作的顺序以及边界条件的判断。如果你想进一步了解最小堆,可以通过LeetCode上的相关题目进行练习和掌握。