authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2018-05-07 12:01:20-04:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2018-05-07 16:50:33-04:00
log3b7aa808920dc96c9219a57a9d0f3ac6f85a18de
tree9170bd455aaa82cf9dd3cf2214035b5677098c2b
parent77a1a216d2b3ceb956869ba1716fbb6c0c7eabe8

add std.SegmentedList.Iterator


1 files changed, 58 insertions(+), 2 deletions(-)

std/segmented_list.zig+58-2
......@@ -86,10 +86,10 @@ pub fn SegmentedList(comptime T: type, comptime prealloc_item_count: usize) type
8686 };
8787 const ShelfIndex = std.math.Log2Int(usize);
8888
89 allocator: &Allocator,
90 len: usize,
9189 prealloc_segment: [prealloc_item_count]T,
9290 dynamic_segments: []&T,
91 allocator: &Allocator,
92 len: usize,
9393
9494 /// Deinitialize with `deinit`
9595 pub fn init(allocator: &Allocator) Self {
......@@ -237,6 +237,54 @@ pub fn SegmentedList(comptime T: type, comptime prealloc_item_count: usize) type
237237 }
238238 }
239239
240 pub const Iterator = struct {
241 list: &Self,
242 index: usize,
243 box_index: usize,
244 shelf_index: ShelfIndex,
245 shelf_size: usize,
246
247 pub fn next(it: &Iterator) ?&T {
248 if (it.index >= it.list.len)
249 return null;
250 if (it.index < prealloc_item_count) {
251 const ptr = &it.list.prealloc_segment[it.index];
252 it.index += 1;
253 if (it.index == prealloc_item_count) {
254 it.box_index = 0;
255 it.shelf_index = 0;
256 it.shelf_size = prealloc_item_count * 2;
257 }
258 return ptr;
259 }
260
261 const ptr = &it.list.dynamic_segments[it.shelf_index][it.box_index];
262 it.index += 1;
263 it.box_index += 1;
264 if (it.box_index == it.shelf_size) {
265 it.shelf_index += 1;
266 it.box_index = 0;
267 it.shelf_size *= 2;
268 }
269 return ptr;
270 }
271 };
272
273 pub fn iterator(self: &Self, start_index: usize) Iterator {
274 var it = Iterator {
275 .list = self,
276 .index = start_index,
277 .shelf_index = undefined,
278 .box_index = undefined,
279 .shelf_size = undefined,
280 };
281 if (start_index >= prealloc_item_count) {
282 it.shelf_index = shelfIndex(start_index);
283 it.box_index = boxIndex(start_index, it.shelf_index);
284 it.shelf_size = shelfSize(it.shelf_index);
285 }
286 return it;
287 }
240288 };
241289}
242290
......@@ -266,6 +314,14 @@ fn testSegmentedList(comptime prealloc: usize, allocator: &Allocator) !void {
266314 assert(*list.at(i) == i32(i + 1));
267315 }}
268316
317 {
318 var it = list.iterator(0);
319 var x: i32 = 1;
320 while (it.next()) |item| : (x += 1) {
321 assert(*item == x);
322 }
323 }
324
269325 assert(??list.pop() == 100);
270326 assert(list.len == 99);
271327