1
0

light washing, fix overflows
Some checks failed
Build and test / test (push) Failing after 1m43s

This commit is contained in:
xeals 2023-12-13 13:51:38 +11:00
parent d80a39e7dc
commit fa7a9aab14
Signed by: xeals
SSH Key Fingerprint: SHA256:pRv+8swQDA+/LuZ7NHj9m006BbKexlNK62OUA01ZZBc

View File

@ -22,8 +22,7 @@ fn hash(alloc: mem.Allocator, pattern: []const u8, groups: []const u8, curr_grou
return try a.toOwnedSlice(); return try a.toOwnedSlice();
} }
// Mystery records to whether they fit. var memo: std.StringHashMap(usize) = undefined;
var memo: std.StringHashMap(u32) = undefined;
fn clone(comptime T: type, alloc: mem.Allocator, s: []const T) ![]T { fn clone(comptime T: type, alloc: mem.Allocator, s: []const T) ![]T {
var a = try alloc.alloc(T, s.len); var a = try alloc.alloc(T, s.len);
@ -31,32 +30,26 @@ fn clone(comptime T: type, alloc: mem.Allocator, s: []const T) ![]T {
return a; return a;
} }
fn solvePattern(alloc: mem.Allocator, pattern: []const u8, groups: []const u8, curr_group: u8) !u32 { fn solvePattern(alloc: mem.Allocator, pattern: []const u8, groups: []const u8, curr_group: u8) !usize {
std.debug.print("{s}, {any}, {}\n", .{ pattern, groups, curr_group });
const h = try hash(alloc, pattern, groups, curr_group); const h = try hash(alloc, pattern, groups, curr_group);
if (memo.get(h)) |m| { if (memo.get(h)) |m| {
alloc.free(h); alloc.free(h);
std.debug.print("== short-circuit {}\n", .{m});
return m; return m;
} }
if (pattern.len == 0) { if (pattern.len == 0) {
std.debug.print("== done {}\n", .{groups.len == 0});
return if (groups.len == 0) 1 else 0; return if (groups.len == 0) 1 else 0;
} }
const res: u32 = b: { const res: usize = b: {
switch (pattern[0]) { switch (pattern[0]) {
'#' => { '#' => {
// Too many # // Too many #
if (groups.len == 0 or curr_group >= groups[0]) { if (groups.len == 0 or curr_group >= groups[0]) {
std.debug.print("== bad fit\n", .{});
break :b 0; break :b 0;
} }
// Special-case last # // Special-case last #
if (pattern.len == 1 and groups.len == 1 and groups[0] == curr_group + 1) { if (pattern.len == 1 and groups.len == 1 and groups[0] == curr_group + 1) {
std.debug.print("== done true\n", .{});
break :b 1; break :b 1;
} }
break :b try solvePattern(alloc, pattern[1..], groups, curr_group + 1); break :b try solvePattern(alloc, pattern[1..], groups, curr_group + 1);
@ -65,7 +58,6 @@ fn solvePattern(alloc: mem.Allocator, pattern: []const u8, groups: []const u8, c
if (curr_group > 0) { if (curr_group > 0) {
if (groups.len == 0 or curr_group != groups[0]) { if (groups.len == 0 or curr_group != groups[0]) {
// Too many # // Too many #
std.debug.print("== bad fit\n", .{});
break :b 0; break :b 0;
} else { } else {
// Group done // Group done
@ -85,7 +77,6 @@ fn solvePattern(alloc: mem.Allocator, pattern: []const u8, groups: []const u8, c
p1[0] = '#'; p1[0] = '#';
p2[0] = '.'; p2[0] = '.';
std.debug.print("=> test ?\n", .{});
break :b try solvePattern(alloc, p1, groups, curr_group) + break :b try solvePattern(alloc, p1, groups, curr_group) +
try solvePattern(alloc, p2, groups, curr_group); try solvePattern(alloc, p2, groups, curr_group);
}, },
@ -93,7 +84,6 @@ fn solvePattern(alloc: mem.Allocator, pattern: []const u8, groups: []const u8, c
} }
}; };
std.debug.print("<= {s}, {any}, {} = {}\n", .{ pattern, groups, curr_group, res });
try memo.put(h, res); try memo.put(h, res);
return res; return res;
@ -109,16 +99,17 @@ fn unfold(alloc: mem.Allocator, input: []const u8, sep: u8) ![]const u8 {
} }
fn solve(alloc: mem.Allocator, input: []const u8) !Solution { fn solve(alloc: mem.Allocator, input: []const u8) !Solution {
memo = std.StringHashMap(u32).init(alloc); memo = std.StringHashMap(usize).init(alloc);
defer memo.deinit(); defer memo.deinit();
var sum1: u32 = 0; var sum1: usize = 0;
var sum2: u32 = 0; var sum2: usize = 0;
var it = util.splitLines(input); var it = util.splitLines(input);
var i: u32 = 0; var i: usize = 1;
while (it.next()) |line| { while (it.next()) |line| {
if (line.len == 0) continue; if (line.len == 0) continue;
std.debug.print("line {} ", .{i});
var lit = util.splitSpace(line); var lit = util.splitSpace(line);
const pattern = lit.next().?; const pattern = lit.next().?;
@ -131,7 +122,6 @@ fn solve(alloc: mem.Allocator, input: []const u8) !Solution {
defer alloc.free(unfolded_pattern); defer alloc.free(unfolded_pattern);
defer alloc.free(unfolded_groups); defer alloc.free(unfolded_groups);
std.debug.print("---- {} ----\n", .{i});
sum1 += try solvePattern(alloc, pattern, groups, 0); sum1 += try solvePattern(alloc, pattern, groups, 0);
sum2 += try solvePattern(alloc, unfolded_pattern, unfolded_groups, 0); sum2 += try solvePattern(alloc, unfolded_pattern, unfolded_groups, 0);
std.debug.print("{} {}\n", .{ sum1, sum2 }); std.debug.print("{} {}\n", .{ sum1, sum2 });
@ -159,34 +149,15 @@ test "silver" {
try std.testing.expectEqual(@as(usize, 21), sln.a); try std.testing.expectEqual(@as(usize, 21), sln.a);
} }
test "gold-2" { test "gold" {
const input = const input =
\\???.### 1,1,3
\\.??..??...?##. 1,1,3 \\.??..??...?##. 1,1,3
; \\?#?#?#?#?#?#?#? 1,3,1,6
const sln = try solve(std.testing.allocator, input);
try std.testing.expectEqual(@as(usize, 16384), sln.b);
}
test "gold-4" {
const input =
\\????.#...#... 4,1,1 \\????.#...#... 4,1,1
;
const sln = try solve(std.testing.allocator, input);
try std.testing.expectEqual(@as(usize, 16), sln.b);
}
test "gold-5" {
const input =
\\????.######..#####. 1,6,5 \\????.######..#####. 1,6,5
;
const sln = try solve(std.testing.allocator, input);
try std.testing.expectEqual(@as(usize, 2500), sln.b);
}
test "gold-6" {
const input =
\\?###???????? 3,2,1 \\?###???????? 3,2,1
; ;
const sln = try solve(std.testing.allocator, input); const sln = try solve(std.testing.allocator, input);
try std.testing.expectEqual(@as(usize, 506250), sln.b); try std.testing.expectEqual(@as(usize, 525152), sln.b);
} }