Class Heap<E, R>

Binary heap with pluggable comparator; supports fast insertion and removal of the top element.

Time O(1), Space O(1)

// Use Heap to sort an array
function heapSort(arr: number[]): number[] {
const heap = new Heap<number>(arr, { comparator: (a, b) => a - b });
const sorted: number[] = [];
while (!heap.isEmpty()) {
sorted.push(heap.poll()!); // Poll minimum element
}
return sorted;
}

const array = [5, 3, 8, 4, 1, 2];
console.log(heapSort(array)); // [1, 2, 3, 4, 5, 8]
// Use Heap to solve top k problems
function topKElements(arr: number[], k: number): number[] {
const heap = new Heap<number>([], { comparator: (a, b) => b - a }); // Max heap
arr.forEach(num => {
heap.add(num);
if (heap.size > k) heap.poll(); // Keep the heap size at K
});
return heap.toArray();
}

const numbers = [10, 30, 20, 5, 15, 25];
console.log(topKElements(numbers, 3)); // [15, 10, 5]
// Use Heap to merge sorted sequences
function mergeSortedSequences(sequences: number[][]): number[] {
const heap = new Heap<{ value: number; seqIndex: number; itemIndex: number }>([], {
comparator: (a, b) => a.value - b.value // Min heap
});

// Initialize heap
sequences.forEach((seq, seqIndex) => {
if (seq.length) {
heap.add({ value: seq[0], seqIndex, itemIndex: 0 });
}
});

const merged: number[] = [];
while (!heap.isEmpty()) {
const { value, seqIndex, itemIndex } = heap.poll()!;
merged.push(value);

if (itemIndex + 1 < sequences[seqIndex].length) {
heap.add({
value: sequences[seqIndex][itemIndex + 1],
seqIndex,
itemIndex: itemIndex + 1
});
}
}

return merged;
}

const sequences = [
[1, 4, 7],
[2, 5, 8],
[3, 6, 9]
];
console.log(mergeSortedSequences(sequences)); // [1, 2, 3, 4, 5, 6, 7, 8, 9]
// Use Heap to dynamically maintain the median
class MedianFinder {
private low: MaxHeap<number>; // Max heap, stores the smaller half
private high: MinHeap<number>; // Min heap, stores the larger half

constructor() {
this.low = new MaxHeap<number>([]);
this.high = new MinHeap<number>([]);
}

addNum(num: number): void {
if (this.low.isEmpty() || num <= this.low.peek()!) this.low.add(num);
else this.high.add(num);

// Balance heaps
if (this.low.size > this.high.size + 1) this.high.add(this.low.poll()!);
else if (this.high.size > this.low.size) this.low.add(this.high.poll()!);
}

findMedian(): number {
if (this.low.size === this.high.size) return (this.low.peek()! + this.high.peek()!) / 2;
return this.low.peek()!;
}
}

const medianFinder = new MedianFinder();
medianFinder.addNum(10);
console.log(medianFinder.findMedian()); // 10
medianFinder.addNum(20);
console.log(medianFinder.findMedian()); // 15
medianFinder.addNum(30);
console.log(medianFinder.findMedian()); // 20
medianFinder.addNum(40);
console.log(medianFinder.findMedian()); // 25
medianFinder.addNum(50);
console.log(medianFinder.findMedian()); // 30
// Use Heap for load balancing
function loadBalance(requests: number[], servers: number): number[] {
const serverHeap = new Heap<{ id: number; load: number }>([], { comparator: (a, b) => a.load - b.load }); // min heap
const serverLoads = new Array(servers).fill(0);

for (let i = 0; i < servers; i++) {
serverHeap.add({ id: i, load: 0 });
}

requests.forEach(req => {
const server = serverHeap.poll()!;
serverLoads[server.id] += req;
server.load += req;
serverHeap.add(server); // The server after updating the load is re-entered into the heap
});

return serverLoads;
}

const requests = [5, 2, 8, 3, 7];
console.log(loadBalance(requests, 3)); // [12, 8, 5]
// Use Heap to schedule tasks
type Task = [string, number];

function scheduleTasks(tasks: Task[], machines: number): Map<number, Task[]> {
const machineHeap = new Heap<{ id: number; load: number }>([], { comparator: (a, b) => a.load - b.load }); // Min heap
const allocation = new Map<number, Task[]>();

// Initialize the load on each machine
for (let i = 0; i < machines; i++) {
machineHeap.add({ id: i, load: 0 });
allocation.set(i, []);
}

// Assign tasks
tasks.forEach(([task, load]) => {
const machine = machineHeap.poll()!;
allocation.get(machine.id)!.push([task, load]);
machine.load += load;
machineHeap.add(machine); // The machine after updating the load is re-entered into the heap
});

return allocation;
}

const tasks: Task[] = [
['Task1', 3],
['Task2', 1],
['Task3', 2],
['Task4', 5],
['Task5', 4]
];
const expectedMap = new Map<number, Task[]>();
expectedMap.set(0, [
['Task1', 3],
['Task4', 5]
]);
expectedMap.set(1, [
['Task2', 1],
['Task3', 2],
['Task5', 4]
]);
console.log(scheduleTasks(tasks, 2)); // expectedMap

Type Parameters

  • E = unknown
  • R = never
    1. Complete Binary Tree: Heaps are typically complete binary trees, meaning every level is fully filled except possibly for the last level, which has nodes as far left as possible.
    2. Heap Properties: Each node in a heap follows a specific order property, which varies depending on the type of heap: Max Heap: The value of each parent node is greater than or equal to the value of its children. Min Heap: The value of each parent node is less than or equal to the value of its children.
    3. Root Node Access: In a heap, the largest element (in a max heap) or the smallest element (in a min heap) is always at the root of the tree.
    4. Efficient Insertion and Deletion: Due to its structure, a heap allows for insertion and deletion operations in logarithmic time (O(log n)).
    5. Managing Dynamic Data Sets: Heaps effectively manage dynamic data sets, especially when frequent access to the largest or smallest elements is required.
    6. Non-linear Search: While a heap allows rapid access to its largest or smallest element, it is less efficient for other operations, such as searching for a specific element, as it is not designed for these tasks.
    7. Efficient Sorting Algorithms: For example, heap sort. Heap sort uses the properties of a heap to sort elements.
    8. Graph Algorithms: Such as Dijkstra's shortest path algorithm and Prime's minimum-spanning tree algorithm, which use heaps to improve performance.

Hierarchy (view full)

Constructors

  • Create a Heap and optionally bulk-insert elements.

    Type Parameters

    • E = unknown
    • R = never

    Parameters

    • Optionalelements: Iterable<E | R, any, any> = []

      Iterable of elements (or raw values if toElementFn is set).

    • Optionaloptions: HeapOptions<E, R>

      Options such as comparator and toElementFn.

    Returns Heap<E, R>

    New Heap instance.

    Time O(N), Space O(N)

Properties

_toElementFn?: ((rawElement: R) => E)

The converter used to transform a raw element (R) into a public element (E).

Time O(1), Space O(1).

Accessors

  • get comparator(): Comparator<E>
  • Get the comparator used to order elements.

    Returns Comparator<E>

    Comparator function.

    Time O(1), Space O(1)

  • get leaf(): undefined | E
  • Get the last leaf element.

    Returns undefined | E

    Last element or undefined.

    Time O(1), Space O(1)

  • get toElementFn(): undefined | ((rawElement: R) => E)
  • Exposes the current toElementFn, if configured.

    Returns undefined | ((rawElement: R) => E)

    The converter function or undefined when not set.

    Time O(1), Space O(1).

Methods

  • (Protected) Create an empty instance of the same concrete class.

    Parameters

    • Optionaloptions: HeapOptions<E, R>

      Options to override comparator or toElementFn.

    Returns this

    A like-kind empty heap instance.

    Time O(1), Space O(1)

  • (Protected) Create a like-kind instance seeded by elements.

    Type Parameters

    • EM
    • RM

    Parameters

    • Optionalelements: Iterable<EM, any, any> | Iterable<RM, any, any> = []

      Iterable of elements or raw values to seed.

    • Optionaloptions: HeapOptions<EM, RM>

      Options forwarded to the constructor.

    Returns Heap<EM, RM>

    A like-kind heap instance.

    Time O(N log N), Space O(N)

  • Internal iterator factory used by the default iterator.

    Returns IterableIterator<E, any, any>

    An iterator over elements.

    Implementations should yield in O(1) per element with O(1) extra space when possible.

  • (Protected) Spawn an empty like-kind heap instance.

    Type Parameters

    • EM
    • RM

    Parameters

    • Optionaloptions: HeapOptions<EM, RM>

      Options forwarded to the constructor.

    Returns Heap<EM, RM>

    An empty like-kind heap instance.

    Time O(1), Space O(1)

  • Returns an iterator over the structure's elements.

    Parameters

    • Rest...args: unknown[]

      Optional iterator arguments forwarded to the internal iterator.

    Returns IterableIterator<E, any, any>

    An IterableIterator<E> that yields the elements in traversal order.

    Producing the iterator is O(1); consuming the entire iterator is Time O(n) with O(1) extra space.

  • Insert an element.

    Parameters

    • element: E

      Element to insert.

    Returns boolean

    True.

    Time O(1) amortized, Space O(1)

  • Insert many elements from an iterable.

    Parameters

    • elements: Iterable<E | R, any, any>

      Iterable of elements or raw values.

    Returns boolean[]

    Array of per-element success flags.

    Time O(N log N), Space O(1)

  • Delete one occurrence of an element.

    Parameters

    • element: E

      Element to delete.

    Returns boolean

    True if an element was removed.

    Time O(N), Space O(1)

  • Delete the first element that matches a predicate.

    Parameters

    • predicate: ((element: E, index: number, heap: this) => boolean)

      Function (element, index, heap) → boolean.

        • (element, index, heap): boolean
        • Parameters

          • element: E
          • index: number
          • heap: this

          Returns boolean

    Returns boolean

    True if an element was removed.

    Time O(N), Space O(1)

  • Traverse the binary heap as a complete binary tree and collect elements.

    Parameters

    • Optionalorder: DFSOrderPattern = 'PRE'

      Traversal order: 'PRE' | 'IN' | 'POST'.

    Returns E[]

    Array of visited elements.

    Time O(N), Space O(H)

  • Tests whether all elements satisfy the predicate.

    Parameters

    • predicate: ElementCallback<E, R, boolean>

      Function invoked for each element with signature (value, index, self).

    • OptionalthisArg: unknown

      Optional this binding for the predicate.

    Returns boolean

    true if every element passes; otherwise false.

    Time O(n) in the worst case; may exit early when the first failure is found. Space O(1).

  • Filter elements into a new heap of the same class.

    Parameters

    • callback: ElementCallback<E, R, boolean>

      Predicate (element, index, heap) → boolean to keep element.

    • OptionalthisArg: unknown

      Value for this inside the callback.

    Returns this

    A new heap with the kept elements.

    Time O(N log N), Space O(N)

  • Finds the first element that satisfies the predicate and returns it.

    Finds the first element of type S (a subtype of E) that satisfies the predicate and returns it.

    Type Parameters

    • S

    Parameters

    • predicate: ElementCallback<E, R, S>

      Type-guard predicate: (value, index, self) => value is S.

    • OptionalthisArg: unknown

      Optional this binding for the predicate.

    Returns undefined | S

    The matched element typed as S, or undefined if not found.

    Time O(n) in the worst case; may exit early on the first match. Space O(1).

  • Restore heap order bottom-up (heapify in-place).

    Returns boolean[]

    Array of per-node results from fixing steps.

    Time O(N), Space O(1)

  • Invokes a callback for each element in iteration order.

    Parameters

    • callbackfn: ElementCallback<E, R, void>

      Function invoked per element with signature (value, index, self).

    • OptionalthisArg: unknown

      Optional this binding for the callback.

    Returns void

    void.

    Time O(n), Space O(1).

  • Map elements into a new heap of possibly different element type.

    Type Parameters

    • EM
    • RM

    Parameters

    • callback: ElementCallback<E, R, EM>

      Mapping function (element, index, heap) → newElement.

    • options: IterableElementBaseOptions<EM, RM> & {
          comparator?: Comparator<EM>;
      } & {
          comparator: Comparator<EM>;
      }

      Options for the output heap, including comparator for EM.

    • OptionalthisArg: unknown

      Value for this inside the callback.

    Returns Heap<EM, RM>

    A new heap with mapped elements.

    Time O(N log N), Space O(N)

  • Map elements into a new heap of the same element type.

    Parameters

    • callback: ElementCallback<E, R, E>

      Mapping function (element, index, heap) → element.

    • OptionalthisArg: unknown

      Value for this inside the callback.

    Returns this

    A new heap with mapped elements.

    Time O(N log N), Space O(N)

  • Get the current top element without removing it.

    Returns undefined | E

    Top element or undefined.

    Time O(1), Space O(1)

  • Remove and return the top element.

    Returns undefined | E

    Top element or undefined.

    Time O(log N), Space O(1)

  • Replace the backing array and rebuild the heap.

    Parameters

    • elements: Iterable<E, any, any>

      Iterable used to refill the heap.

    Returns boolean[]

    Array of per-node results from fixing steps.

    Time O(N), Space O(N)

  • Set the equality comparator used by has/delete operations.

    Parameters

    • equals: ((a: E, b: E) => boolean)

      Equality predicate (a, b) → boolean.

        • (a, b): boolean
        • Parameters

          Returns boolean

    Returns this

    This heap.

    Time O(1), Space O(1)

  • Tests whether at least one element satisfies the predicate.

    Parameters

    • predicate: ElementCallback<E, R, boolean>

      Function invoked for each element with signature (value, index, self).

    • OptionalthisArg: unknown

      Optional this binding for the predicate.

    Returns boolean

    true if any element passes; otherwise false.

    Time O(n) in the worst case; may exit early on first success. Space O(1).

  • Return all elements in ascending order by repeatedly polling.

    Returns E[]

    Sorted array of elements.

    Time O(N log N), Space O(N)

  • Create a heap of the same class from an iterable.

    Type Parameters

    Parameters

    • this: Object
    • Optionalelements: Iterable<T | R, any, any>

      Iterable of elements or raw records.

    • Optionaloptions: HeapOptions<T, R>

      Heap options including comparator.

    Returns S

    A new heap instance of this class.

    Time O(N), Space O(N)

  • Build a Heap from an iterable in linear time given a comparator.

    Type Parameters

    • EE = unknown
    • RR = never

    Parameters

    • elements: Iterable<EE, any, any>

      Iterable of elements.

    • options: HeapOptions<EE, RR>

      Heap options including comparator.

    Returns Heap<EE, RR>

    A new Heap built from elements.

    Time O(N), Space O(N)