diff options
author | 2021-04-28 21:58:02 -0700 | |
---|---|---|
committer | 2021-04-28 21:58:02 -0700 | |
commit | cabe773a4f0a12e411f9f3c9698da6bbd90ec474 (patch) | |
tree | c20cfd9ba22c4ca999c850edb04012d94d72ccb5 /src/string_immutable.zig | |
parent | 435a6e9b187168d869024d1002951e4bfa76333a (diff) | |
download | bun-cabe773a4f0a12e411f9f3c9698da6bbd90ec474.tar.gz bun-cabe773a4f0a12e411f9f3c9698da6bbd90ec474.tar.zst bun-cabe773a4f0a12e411f9f3c9698da6bbd90ec474.zip |
wip
Former-commit-id: b37acf309c8f42d49dc47eea446f89a3dbe9f6e2
Diffstat (limited to 'src/string_immutable.zig')
-rw-r--r-- | src/string_immutable.zig | 35 |
1 files changed, 35 insertions, 0 deletions
diff --git a/src/string_immutable.zig b/src/string_immutable.zig index 116c17c00..d0dffd49e 100644 --- a/src/string_immutable.zig +++ b/src/string_immutable.zig @@ -237,3 +237,38 @@ pub fn containsNonBmpCodePointUTF16(_text: JavascriptString) bool { return false; } + +/// Super simple "perfect hash" algorithm +/// Only really useful for switching on strings +// TODO: can we auto detect and promote the underlying type? +pub fn ExactSizeMatcher(comptime max_bytes: usize) type { + const T = std.meta.Int( + .unsigned, + max_bytes * 8, + ); + + return struct { + pub fn match(str: anytype) T { + return hash(str) orelse std.math.maxInt(T); + } + + pub fn case(comptime str: []const u8) T { + return hash(str) orelse std.math.maxInt(T); + } + + fn hash(str: anytype) ?T { + // if (str.len > max_bytes) return null; + var tmp = [_]u8{0} ** max_bytes; + std.mem.copy(u8, &tmp, str); + return std.mem.readIntNative(T, &tmp); + } + }; +} + +const eight = ExactSizeMatcher(8); + +test "ExactSizeMatcher" { + const word = "yield"; + expect(eight.match(word) == eight.case("yield")); + expect(eight.match(word) != eight.case("yields")); +} |