Merge pull request #981 from BraedonWooding/ArrayIteratorUnifiedSyntax
ArrayList iterator, unifying API of HashMap and its derivatives
This commit is contained in:
commit
33fa87a9d8
@ -44,6 +44,10 @@ pub fn AlignedArrayList(comptime T: type, comptime A: u29) type{
|
||||
return l.toSliceConst()[n];
|
||||
}
|
||||
|
||||
pub fn count(self: &const Self) usize {
|
||||
return self.len;
|
||||
}
|
||||
|
||||
/// ArrayList takes ownership of the passed in slice. The slice must have been
|
||||
/// allocated with `allocator`.
|
||||
/// Deinitialize with `deinit` or use `toOwnedSlice`.
|
||||
@ -128,6 +132,27 @@ pub fn AlignedArrayList(comptime T: type, comptime A: u29) type{
|
||||
return null;
|
||||
return self.pop();
|
||||
}
|
||||
|
||||
pub const Iterator = struct {
|
||||
list: &const Self,
|
||||
// how many items have we returned
|
||||
count: usize,
|
||||
|
||||
pub fn next(it: &Iterator) ?T {
|
||||
if (it.count >= it.list.len) return null;
|
||||
const val = it.list.at(it.count);
|
||||
it.count += 1;
|
||||
return val;
|
||||
}
|
||||
|
||||
pub fn reset(it: &Iterator) void {
|
||||
it.count = 0;
|
||||
}
|
||||
};
|
||||
|
||||
pub fn iterator(self: &Self) Iterator {
|
||||
return Iterator { .list = self, .count = 0 };
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@ -157,6 +182,35 @@ test "basic ArrayList test" {
|
||||
assert(list.len == 9);
|
||||
}
|
||||
|
||||
test "iterator ArrayList test" {
|
||||
var list = ArrayList(i32).init(debug.global_allocator);
|
||||
defer list.deinit();
|
||||
|
||||
try list.append(1);
|
||||
try list.append(2);
|
||||
try list.append(3);
|
||||
|
||||
var count : i32 = 0;
|
||||
var it = list.iterator();
|
||||
while (it.next()) |next| {
|
||||
assert(next == count + 1);
|
||||
count += 1;
|
||||
}
|
||||
|
||||
assert(count == 3);
|
||||
assert(it.next() == null);
|
||||
it.reset();
|
||||
count = 0;
|
||||
while (it.next()) |next| {
|
||||
assert(next == count + 1);
|
||||
count += 1;
|
||||
if (count == 2) break;
|
||||
}
|
||||
|
||||
it.reset();
|
||||
assert(?? it.next() == 1);
|
||||
}
|
||||
|
||||
test "insert ArrayList test" {
|
||||
var list = ArrayList(i32).init(debug.global_allocator);
|
||||
defer list.deinit();
|
||||
@ -174,4 +228,4 @@ test "insert ArrayList test" {
|
||||
const items = []const i32 { 1 };
|
||||
try list.insertSlice(0, items[0..0]);
|
||||
assert(list.items[0] == 5);
|
||||
}
|
||||
}
|
@ -50,7 +50,7 @@ pub const BufMap = struct {
|
||||
}
|
||||
|
||||
pub fn count(self: &const BufMap) usize {
|
||||
return self.hash_map.size;
|
||||
return self.hash_map.count();
|
||||
}
|
||||
|
||||
pub fn iterator(self: &const BufMap) BufMapHashMap.Iterator {
|
||||
@ -87,4 +87,4 @@ test "BufMap" {
|
||||
|
||||
bufmap.delete("x");
|
||||
assert(0 == bufmap.count());
|
||||
}
|
||||
}
|
@ -38,7 +38,7 @@ pub const BufSet = struct {
|
||||
}
|
||||
|
||||
pub fn count(self: &const BufSet) usize {
|
||||
return self.hash_map.size;
|
||||
return self.hash_map.count();
|
||||
}
|
||||
|
||||
pub fn iterator(self: &const BufSet) BufSetHashMap.Iterator {
|
||||
@ -59,4 +59,3 @@ pub const BufSet = struct {
|
||||
return result;
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -54,6 +54,14 @@ pub fn HashMap(comptime K: type, comptime V: type,
|
||||
}
|
||||
unreachable; // no next item
|
||||
}
|
||||
|
||||
// Reset the iterator to the initial index
|
||||
pub fn reset(it: &Iterator) void {
|
||||
it.count = 0;
|
||||
it.index = 0;
|
||||
// Resetting the modification count too
|
||||
it.initial_modification_count = it.hm.modification_count;
|
||||
}
|
||||
};
|
||||
|
||||
pub fn init(allocator: &Allocator) Self {
|
||||
@ -79,6 +87,10 @@ pub fn HashMap(comptime K: type, comptime V: type,
|
||||
hm.incrementModificationCount();
|
||||
}
|
||||
|
||||
pub fn count(hm: &const Self) usize {
|
||||
return hm.size;
|
||||
}
|
||||
|
||||
/// Returns the value that was already there.
|
||||
pub fn put(hm: &Self, key: K, value: &const V) !?V {
|
||||
if (hm.entries.len == 0) {
|
||||
@ -258,10 +270,49 @@ test "basic hash map usage" {
|
||||
assert(map.get(2) == null);
|
||||
}
|
||||
|
||||
test "iterator hash map" {
|
||||
var direct_allocator = std.heap.DirectAllocator.init();
|
||||
defer direct_allocator.deinit();
|
||||
|
||||
var reset_map = HashMap(i32, i32, hash_i32, eql_i32).init(&direct_allocator.allocator);
|
||||
defer reset_map.deinit();
|
||||
|
||||
assert((reset_map.put(1, 11) catch unreachable) == null);
|
||||
assert((reset_map.put(2, 22) catch unreachable) == null);
|
||||
assert((reset_map.put(3, 33) catch unreachable) == null);
|
||||
|
||||
var keys = []i32 { 1, 2, 3 };
|
||||
var values = []i32 { 11, 22, 33 };
|
||||
|
||||
var it = reset_map.iterator();
|
||||
var count : usize = 0;
|
||||
while (it.next()) |next| {
|
||||
assert(next.key == keys[count]);
|
||||
assert(next.value == values[count]);
|
||||
count += 1;
|
||||
}
|
||||
|
||||
assert(count == 3);
|
||||
assert(it.next() == null);
|
||||
it.reset();
|
||||
count = 0;
|
||||
while (it.next()) |next| {
|
||||
assert(next.key == keys[count]);
|
||||
assert(next.value == values[count]);
|
||||
count += 1;
|
||||
if (count == 2) break;
|
||||
}
|
||||
|
||||
it.reset();
|
||||
var entry = ?? it.next();
|
||||
assert(entry.key == keys[0]);
|
||||
assert(entry.value == values[0]);
|
||||
}
|
||||
|
||||
fn hash_i32(x: i32) u32 {
|
||||
return @bitCast(u32, x);
|
||||
}
|
||||
|
||||
fn eql_i32(a: i32, b: i32) bool {
|
||||
return a == b;
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user