Fix bugs in memory module and add unit tests
continuous-integration/drone/push Build is passing Details

This commit is contained in:
kayomn 2022-10-02 13:03:55 +01:00
parent 3ca0bd5724
commit 71d5d696bd
1 changed files with 45 additions and 16 deletions

View File

@ -14,9 +14,6 @@ pub fn Spliterator(comptime Element: type) type {
/// ///
/// Returns `true` if there is more data to be processed, otherwise `false`. /// Returns `true` if there is more data to be processed, otherwise `false`.
/// ///
/// Note that [Spliterator.next] implicitly calls this function to determine if it should
/// return another slice or `null`.
///
pub fn hasNext(self: Self) bool { pub fn hasNext(self: Self) bool {
return (self.source.len != 0); return (self.source.len != 0);
} }
@ -26,27 +23,55 @@ pub fn Spliterator(comptime Element: type) type {
/// [Spliterator.delimiter], or `null` if there is no more data to be processed. /// [Spliterator.delimiter], or `null` if there is no more data to be processed.
/// ///
pub fn next(self: *Self) ?[]const Element { pub fn next(self: *Self) ?[]const Element {
if (self.delimiter.len == 0) { if (!self.hasNext()) return null;
defer self.source = self.source[self.source.len .. 0];
return self.source; if (std.mem.indexOfPos(Element, self.source, 0, self.delimiter)) |index| {
defer self.source = self.source[(index + self.delimiter.len) .. self.source.len];
return self.source[0 .. index];
} }
while (self.hasNext()) { defer self.source = self.source[self.source.len .. self.source.len];
var cursor = @as(usize, 0);
var window = self.source[cursor .. (self.source.len - cursor)];
defer self.source = window; return self.source;
if (std.mem.eql(Element, window, self.delimiter))
return self.source[cursor .. self.delimiter.len];
}
return null;
} }
}; };
} }
test {
const testing = std.testing;
// Single-character delimiter.
{
var spliterator = Spliterator(u8){
.source = "single.character.separated.hello.world",
.delimiter = ".",
};
const components = [_][]const u8{"single", "character", "separated", "hello", "world"};
var index = @as(usize, 0);
while (spliterator.next()) |split| : (index += 1) {
try testing.expect(std.mem.eql(u8, split, components[index]));
}
}
// Multi-character delimiter.
{
var spliterator = Spliterator(u8){
.source = "finding a needle in a needle stack",
.delimiter = "needle",
};
const components = [_][]const u8{"finding a ", " in a ", " stack"};
var index = @as(usize, 0);
while (spliterator.next()) |split| : (index += 1) {
try testing.expect(std.mem.eql(u8, split, components[index]));
}
}
}
/// ///
/// Searches the slice of `Data` referenced by `data` for the first instance of `sought_datum`, /// Searches the slice of `Data` referenced by `data` for the first instance of `sought_datum`,
/// returning its index or `null` if it could not be found. /// returning its index or `null` if it could not be found.
@ -56,3 +81,7 @@ pub fn findFirst(comptime Data: type, data: []const Data, sought_datum: Data) ?u
return null; return null;
} }
test {
try std.testing.expectEqual(findFirst(u8, "1234567890", '7'), 6);
}