authorgravatar for joachim.schmidt557@outlook.comJoachim Schmidt <joachim.schmidt557@outlook.com> 2022-05-26 18:23:07+02:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2022-05-26 14:50:24-04:00
log7deae071014237e995ec3017825f7534305ec0c4
tree4683875d2ac8cde512eee25d54238ceb4f0e11d0
parentb08d32ceb5aac5b1ba73c84449c6afee630710bb

std.PriorityQueue: fix missing siftUp in remove

When the replacement node is smaller than its parent, we need to sift up instead of sifting down.

1 files changed, 27 insertions(+), 1 deletions(-)

lib/std/priority_queue.zig+27-1
......@@ -100,7 +100,19 @@ pub fn PriorityQueue(comptime T: type, comptime Context: type, comptime compareF
100100 const item = self.items[index];
101101 self.items[index] = last;
102102 self.len -= 1;
103 siftDown(self, index);
103
104 if (index == 0) {
105 siftDown(self, index);
106 } else {
107 const parent_index = ((index - 1) >> 1);
108 const parent = self.items[parent_index];
109 if (compareFn(self.context, last, parent) == .gt) {
110 siftDown(self, index);
111 } else {
112 siftUp(self, index);
113 }
114 }
115
104116 return item;
105117 }
106118
......@@ -576,6 +588,20 @@ test "std.PriorityQueue: update same max heap" {
576588 try expectEqual(@as(u32, 1), queue.remove());
577589}
578590
591test "std.PriorityQueue: siftUp in remove" {
592 var queue = PQlt.init(testing.allocator, {});
593 defer queue.deinit();
594
595 try queue.addSlice(&.{ 0, 1, 100, 2, 3, 101, 102, 4, 5, 6, 7, 103, 104, 105, 106, 8 });
596
597 _ = queue.removeIndex(std.mem.indexOfScalar(u32, queue.items[0..queue.len], 102).?);
598
599 const sorted_items = [_]u32{ 0, 1, 2, 3, 4, 5, 6, 7, 8, 100, 101, 103, 104, 105, 106 };
600 for (sorted_items) |e| {
601 try expectEqual(e, queue.remove());
602 }
603}
604
579605fn contextLessThan(context: []const u32, a: usize, b: usize) Order {
580606 return std.math.order(context[a], context[b]);
581607}