Add list.Head.prependList/appendList

The existing insertList never compiled.
This commit is contained in:
Isaac Freund
2023-02-27 13:16:11 +01:00
parent 45c11bb3ec
commit e88586a81a
2 changed files with 35 additions and 14 deletions

View File

@@ -27,23 +27,31 @@ pub fn main() void {
var one = B{ .data = 1 }; var one = B{ .data = 1 };
var two = B{ .data = 2 }; var two = B{ .data = 2 };
var three = B{ .data = 3 }; var three = B{ .data = 3 };
var four = B{ .data = 4 };
var five = B{ .data = 5 };
std.debug.print("length: {} empty: {}\n", .{ a.length(), a.empty() }); std.debug.print("length: {} empty: {}\n", .{ a.length(), a.empty() });
a.append(&one); a.append(&one);
a.append(&two); a.append(&two);
a.append(&three); a.append(&three);
a.append(&four);
a.append(&five); std.debug.print("length: {} empty: {}\n", .{ a.length(), a.empty() });
var b: wl.list.Head(B, .link) = undefined;
b.init();
var four = B{ .data = 4 };
var five = B{ .data = 5 };
b.append(&four);
b.append(&five);
a.appendList(&b);
std.debug.print("length: {} empty: {}\n", .{ a.length(), a.empty() }); std.debug.print("length: {} empty: {}\n", .{ a.length(), a.empty() });
{ {
std.debug.print("forward\n", .{}); std.debug.print("forward\n", .{});
var it = a.iterator(.forward); var it = a.iterator(.forward);
while (it.next()) |b| std.debug.print("{}\n", .{b.data}); while (it.next()) |x| std.debug.print("{}\n", .{x.data});
} }
three.link.swapWith(&four.link); three.link.swapWith(&four.link);
@@ -51,7 +59,7 @@ pub fn main() void {
{ {
std.debug.print("reverse swapped 3/4\n", .{}); std.debug.print("reverse swapped 3/4\n", .{});
var it = a.iterator(.reverse); var it = a.iterator(.reverse);
while (it.next()) |b| std.debug.print("{}\n", .{b.data}); while (it.next()) |x| std.debug.print("{}\n", .{x.data});
} }
} }
{ {

View File

@@ -406,6 +406,17 @@ pub const list = struct {
old_other_prev.insert(link); old_other_prev.insert(link);
} }
} }
/// private helper that doesn't handle empty lists and assumes that
/// other is the link of a Head.
fn insertList(link: *Link, other: *Link) void {
other.next.?.prev = link;
other.prev.?.next = link.next;
link.next.?.prev = other.prev;
link.next = other.next;
other.* = .{ .prev = null, .next = null };
}
}; };
pub const Direction = enum { pub const Direction = enum {
@@ -463,6 +474,16 @@ pub const list = struct {
head.link.prev.?.insert(link); head.link.prev.?.insert(link);
} }
pub fn prependList(head: *Self, other: *Self) void {
if (other.empty()) return;
head.link.insertList(&other.link);
}
pub fn appendList(head: *Self, other: *Self) void {
if (other.empty()) return;
head.link.prev.?.insertList(&other.link);
}
pub fn length(head: *const Self) usize { pub fn length(head: *const Self) usize {
var count: usize = 0; var count: usize = 0;
var current = head.link.next.?; var current = head.link.next.?;
@@ -476,14 +497,6 @@ pub const list = struct {
return head.link.next == &head.link; return head.link.next == &head.link;
} }
pub fn insertList(head: *Self, other: *Self) void {
if (other.empty()) return;
other.link.next.?.prev = head.link;
other.link.prev.?.next = head.link.next;
head.link.next.?.prev = other.link.prev;
head.link.next = other.link.next;
}
/// Removal of elements during iteration is illegal /// Removal of elements during iteration is illegal
pub fn Iterator(comptime direction: Direction) type { pub fn Iterator(comptime direction: Direction) type {
return struct { return struct {