Skip to content

Commit f65344f

Browse files
authored
Add binary heap (min-heap) implementation (#296)
1 parent 65d4564 commit f65344f

1 file changed

Lines changed: 113 additions & 0 deletions

File tree

‎data_structures/binary_heap.r‎

Lines changed: 113 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,113 @@
1+
# A binary heap is a complete binary tree where each node is smaller than or
2+
# equal to its children (min-heap). The minimum is always at the root.
3+
#
4+
# To insert a value, add it as the last node and swap it upward
5+
# until the heap property holds (sift up).
6+
#
7+
# To remove the minimum, move the last node to the root and swap it
8+
# downward until the heap property holds (sift down).
9+
#
10+
# Time Complexities:
11+
# - Push (insert): O(log n)
12+
# - Pop (extract min): O(log n)
13+
# - Peek: O(1)
14+
#
15+
# Space Complexity: O(n)
16+
#
17+
# Applications:
18+
# - Priority queues (task scheduling, process management)
19+
# - Dijkstra's shortest path algorithm
20+
# - Heap sort
21+
# - Finding the k smallest/largest elements (Top-K)
22+
# - Event-driven simulation
23+
#
24+
# Example usage:
25+
# h <- c() # create an empty heap
26+
# h <- push(h, 5) # insert values
27+
# h <- push(h, 3)
28+
# h <- push(h, 8)
29+
# peek(h) # view the minimum (3) without removing
30+
# res <- pop(h) # extract the minimum
31+
# res$value # -> 3 (the minimum that was removed)
32+
# res$heap # -> the heap after removal
33+
34+
35+
push <- function(heap, value) {
36+
37+
heap <- c(heap, value)
38+
i <- length(heap)
39+
40+
while (i > 1) {
41+
42+
p <- i %/% 2
43+
44+
if (heap[p] > heap[i]){
45+
heap[c(p, i)] <- heap[c(i, p)]
46+
i <- p
47+
}
48+
else {
49+
break
50+
}
51+
}
52+
return(heap)
53+
}
54+
55+
pop <- function(heap) {
56+
if (length(heap) == 0){
57+
stop("Heap underflow: cannot pop from an empty heap")
58+
}
59+
60+
min_value <- heap[1]
61+
62+
heap[1] <- heap[length(heap)]
63+
heap <- heap[-length(heap)]
64+
65+
i <- 1
66+
child <- 0
67+
68+
while (2 * i <= length(heap)){
69+
if ((2 * i + 1 <= length(heap) && heap[2 * i + 1] < heap[2 * i])){
70+
child <- 2 * i + 1
71+
}
72+
else {
73+
child <- 2 * i
74+
}
75+
76+
if (heap[child] < heap[i]){
77+
heap[c(child, i)] <- heap[c(i, child)]
78+
i <- child
79+
}
80+
else {
81+
break
82+
}
83+
}
84+
85+
return(list(value = min_value, heap = heap))
86+
}
87+
88+
peek <- function(heap) {
89+
if (length(heap) == 0){
90+
stop("Heap underflow: cannot peek")
91+
}
92+
return(heap[1])
93+
}
94+
95+
# Test
96+
if (sys.nframe() == 0){
97+
h <- c()
98+
h <- push(h, 5)
99+
h <- push(h, 3)
100+
h <- push(h, 8)
101+
h <- push(h, 1)
102+
h <- push(h, 9)
103+
h <- push(h, 2)
104+
105+
print(peek(h))
106+
print(h)
107+
108+
res <- pop(h)
109+
print(res$value)
110+
print(res$heap)
111+
}
112+
113+

0 commit comments

Comments
 (0)