Skip to content

Commit a69914d

Browse files
fix: _shiftDown refactored and corrected TheAlgorithms#1298
1 parent ffdd09a commit a69914d

File tree

2 files changed

+30
-71
lines changed

2 files changed

+30
-71
lines changed

Data-Structures/Heap/KeyPriorityQueue.js

Lines changed: 29 additions & 50 deletions
Original file line numberDiff line numberDiff line change
@@ -85,48 +85,43 @@ class KeyPriorityQueue {
8585
const currPos = this.keys[key]
8686
this._heap[currPos][1] = priority
8787
const parentPos = getParentPosition(currPos)
88-
const currPriority = this._heap[currPos][1]
89-
let parentPriority = Infinity
90-
if (parentPos >= 0) {
91-
parentPriority = this._heap[parentPos][1]
92-
}
88+
const currPriority = this._getPriorityOrInfinite(currPos)
89+
const parentPriority = this._getPriorityOrInfinite(parentPos)
9390
const [child1Pos, child2Pos] = getChildrenPosition(currPos)
94-
let [child1Priority, child2Priority] = [Infinity, Infinity]
95-
if (child1Pos < this._heap.length) {
96-
child1Priority = this._heap[child1Pos][1]
97-
}
98-
if (child2Pos < this._heap.length) {
99-
child2Priority = this._heap[child2Pos][1]
100-
}
91+
const child1Priority = this._getPriorityOrInfinite(child1Pos)
92+
const child2Priority = this._getPriorityOrInfinite(child2Pos)
10193

10294
if (parentPos >= 0 && parentPriority > currPriority) {
10395
this._shiftUp(currPos)
104-
} else if (child2Pos < this._heap.length &&
105-
(child1Priority < currPriority || child2Priority < currPriority)) {
96+
} else if (child1Priority < currPriority || child2Priority < currPriority) {
10697
this._shiftDown(currPos)
10798
}
10899
}
109100

101+
_getPriorityOrInfinite (position) {
102+
// Helper function, returns priority of the node, or Infinite if no node corresponds to this position
103+
if (position >= 0 && position < this._heap.length) {
104+
return this._heap[position][1]
105+
}
106+
else {
107+
return Infinity
108+
}
109+
}
110+
110111
_shiftUp(position) {
111112
// Helper function to shift up a node to proper position (equivalent to bubbleUp)
112113
let currPos = position
113114
let parentPos = getParentPosition(currPos)
114-
let currPriority = this._heap[currPos][1]
115-
let parentPriority = Infinity
116-
if (parentPos >= 0) {
117-
parentPriority = this._heap[parentPos][1]
118-
}
115+
let currPriority = this._getPriorityOrInfinite(currPos)
116+
let parentPriority = this._getPriorityOrInfinite(parentPos)
119117

120118
while (parentPos >= 0 && parentPriority > currPriority) {
121119
this._swap(currPos, parentPos)
122120
currPos = parentPos
123121
parentPos = getParentPosition(currPos)
124-
currPriority = this._heap[currPos][1]
125-
try {
126-
parentPriority = this._heap[parentPos][1]
127-
} catch (error) {
128-
parentPriority = Infinity
129-
}
122+
currPriority = this._getPriorityOrInfinite(currPos)
123+
parentPriority = this._getPriorityOrInfinite(parentPos)
124+
130125
}
131126
this.keys[this._heap[currPos][0]] = currPos
132127
}
@@ -135,22 +130,15 @@ class KeyPriorityQueue {
135130
// Helper function to shift down a node to proper position (equivalent to bubbleDown)
136131
let currPos = position
137132
let [child1Pos, child2Pos] = getChildrenPosition(currPos)
138-
let [child1Priority, child2Priority] = [Infinity, Infinity]
139-
if (child1Pos < this._heap.length) {
140-
child1Priority = this._heap[child1Pos][1]
141-
}
142-
if (child2Pos < this._heap.length) {
143-
child2Priority = this._heap[child2Pos][1]
144-
}
145-
let currPriority
146-
try {
147-
currPriority = this._heap[currPos][1]
148-
} catch {
133+
let child1Priority = this._getPriorityOrInfinite(child1Pos)
134+
let child2Priority = this._getPriorityOrInfinite(child2Pos)
135+
let currPriority = this._getPriorityOrInfinite(currPos)
136+
137+
if (currPriority == Infinity) {
149138
return
150139
}
151140

152-
while (child2Pos < this._heap.length &&
153-
(child1Priority < currPriority || child2Priority < currPriority)) {
141+
while (child1Priority < currPriority || child2Priority < currPriority) {
154142
if (child1Priority < currPriority && child1Priority < child2Priority) {
155143
this._swap(child1Pos, currPos)
156144
currPos = child1Pos
@@ -159,18 +147,9 @@ class KeyPriorityQueue {
159147
currPos = child2Pos
160148
}
161149
[child1Pos, child2Pos] = getChildrenPosition(currPos)
162-
try {
163-
[child1Priority, child2Priority] = [this._heap[child1Pos][1], this._heap[child2Pos][1]]
164-
} catch (error) {
165-
[child1Priority, child2Priority] = [Infinity, Infinity]
166-
}
167-
168-
currPriority = this._heap[currPos][1]
169-
}
170-
this.keys[this._heap[currPos][0]] = currPos
171-
if (child1Pos < this._heap.length && child1Priority < currPriority) {
172-
this._swap(child1Pos, currPos)
173-
this.keys[this._heap[child1Pos][0]] = child1Pos
150+
child1Priority = this._getPriorityOrInfinite(child1Pos)
151+
child2Priority = this._getPriorityOrInfinite(child2Pos)
152+
currPriority = this._getPriorityOrInfinite(currPos)
174153
}
175154
}
176155

Data-Structures/Heap/test/KeyPriorityQueue.test.js

Lines changed: 1 addition & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,5 @@
11
import { KeyPriorityQueue } from '../KeyPriorityQueue.js'
22

3-
describe('KeyPriorityQueue', () => {
4-
5-
test('Check heap correctly ordered', () => {
6-
// create queue and fill it
7-
const priorities = [5, 2, 4, 1, 7, 6, 3, 8]
8-
const queue = new KeyPriorityQueue()
9-
for (let i = 0; i < priorities.length; i++) {
10-
queue.push(i, priorities[i])
11-
}
12-
13-
// result from popping all elements from the queue
14-
let res = []
15-
while (!queue.isEmpty()) {
16-
res.push(queue.pop())
17-
}
18-
19-
expect(res).toEqual([1, 2, 3, 5, 7, 6, 4, 8])
20-
})
21-
})
22-
233
describe('Method isEmpty', () => {
244

255
test('Check heap is empty', () => {
@@ -119,7 +99,7 @@ describe('Method update', () => {
11999
queue.push(3, 11)
120100
// create expected queue
121101
const expectedQueue = new KeyPriorityQueue()
122-
expectedQueue.push(0, 3)
102+
expectedQueue.push(0, 2)
123103
expectedQueue.push(1, 5)
124104
expectedQueue.push(2, 7)
125105
expectedQueue.push(3, 11)

0 commit comments

Comments
 (0)