Skip to content

Commit 3411b5e

Browse files
committed
std.mem: add cut and cutScalar and example usage
1 parent dd2f1cb commit 3411b5e

File tree

2 files changed

+40
-6
lines changed

2 files changed

+40
-6
lines changed

lib/std/mem.zig

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3099,6 +3099,44 @@ test cutSuffix {
30993099
try testing.expectEqual(null, cutSuffix(u8, "foobar", "baz"));
31003100
}
31013101

3102+
/// Returns slice of `haystack` before and after `needle`, or `null` if not
3103+
/// found.
3104+
///
3105+
/// See also:
3106+
/// * `cutScalar`
3107+
/// * `split`
3108+
/// * `tokenizeAny`
3109+
pub fn cut(comptime T: type, haystack: []const T, needle: []const T) ?struct { []const T, []const T } {
3110+
const index = indexOf(T, haystack, needle) orelse return null;
3111+
return .{ haystack[0..index], haystack[index + needle.len ..] };
3112+
}
3113+
3114+
test cut {
3115+
try testing.expectEqual(null, cut(u8, "a b c", "B"));
3116+
const before, const after = cut(u8, "a be c", "be") orelse return error.TestFailed;
3117+
try testing.expectEqualStrings("a ", before);
3118+
try testing.expectEqualStrings(" c", after);
3119+
}
3120+
3121+
/// Returns slice of `haystack` before and after `needle`, or `null` if not
3122+
/// found.
3123+
///
3124+
/// See also:
3125+
/// * `cut`
3126+
/// * `splitScalar`
3127+
/// * `tokenizeScalar`
3128+
pub fn cutScalar(comptime T: type, haystack: []const T, needle: T) ?struct { []const T, []const T } {
3129+
const index = indexOfScalar(T, haystack, needle) orelse return null;
3130+
return .{ haystack[0..index], haystack[index + 1 ..] };
3131+
}
3132+
3133+
test cutScalar {
3134+
try testing.expectEqual(null, cutScalar(u8, "a b c", 'B'));
3135+
const before, const after = cutScalar(u8, "a b c", 'b') orelse return error.TestFailed;
3136+
try testing.expectEqualStrings("a ", before);
3137+
try testing.expectEqualStrings(" c", after);
3138+
}
3139+
31023140
/// Delimiter type for tokenization and splitting operations.
31033141
pub const DelimiterType = enum { sequence, any, scalar };
31043142

src/main.zig

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1077,9 +1077,7 @@ fn buildOutputType(
10771077
.value = value,
10781078
});
10791079
} else if (mem.cutPrefix(u8, arg, "-M")) |rest| {
1080-
var it = mem.splitScalar(u8, rest, '=');
1081-
const mod_name = it.first();
1082-
const root_src_orig = if (it.peek() != null) it.rest() else null;
1080+
const mod_name, const root_src_orig = mem.cutScalar(u8, rest, '=') orelse .{ rest, null };
10831081
try handleModArg(
10841082
arena,
10851083
mod_name,
@@ -1343,9 +1341,7 @@ fn buildOutputType(
13431341
} else {
13441342
dev.check(.network_listen);
13451343
// example: --listen 127.0.0.1:9000
1346-
var it = std.mem.splitScalar(u8, next_arg, ':');
1347-
const host = it.next().?;
1348-
const port_text = it.next() orelse "14735";
1344+
const host, const port_text = mem.cutScalar(u8, next_arg, ':') orelse .{ next_arg, "14735" };
13491345
const port = std.fmt.parseInt(u16, port_text, 10) catch |err|
13501346
fatal("invalid port number: '{s}': {s}", .{ port_text, @errorName(err) });
13511347
listen = .{ .ip4 = std.net.Ip4Address.parse(host, port) catch |err|

0 commit comments

Comments
 (0)