This commit is contained in:
parent
0b6eda2892
commit
992673f784
107
src/day15.zig
Normal file
107
src/day15.zig
Normal file
@ -0,0 +1,107 @@
|
|||||||
|
const std = @import("std");
|
||||||
|
const util = @import("util.zig");
|
||||||
|
const mem = std.mem;
|
||||||
|
|
||||||
|
pub fn main() !void {
|
||||||
|
const input = @embedFile("data/day15.txt");
|
||||||
|
const sln = try solve(util.gpa, input);
|
||||||
|
std.debug.print("{d}\n", .{sln.a});
|
||||||
|
std.debug.print("{d}\n", .{sln.b});
|
||||||
|
}
|
||||||
|
|
||||||
|
const Solution = struct {
|
||||||
|
a: usize,
|
||||||
|
b: usize,
|
||||||
|
};
|
||||||
|
|
||||||
|
fn hash(input: []const u8) u32 {
|
||||||
|
var v: u32 = 0;
|
||||||
|
for (input) |c| {
|
||||||
|
v += c;
|
||||||
|
v *= 17;
|
||||||
|
v %= 256;
|
||||||
|
}
|
||||||
|
return v;
|
||||||
|
}
|
||||||
|
|
||||||
|
fn solve(alloc: mem.Allocator, input: []const u8) !Solution {
|
||||||
|
const trimmed = mem.trimRight(u8, input, "\n\r");
|
||||||
|
|
||||||
|
var hash_sum: u32 = 0;
|
||||||
|
var it = util.split(trimmed, ',');
|
||||||
|
while (it.next()) |line| {
|
||||||
|
if (line.len == 0) continue;
|
||||||
|
hash_sum += hash(line);
|
||||||
|
}
|
||||||
|
|
||||||
|
var boxes: [256]?std.StringArrayHashMap(u8) = [_]?std.StringArrayHashMap(u8){null} ** 256;
|
||||||
|
it = util.split(trimmed, ',');
|
||||||
|
while (it.next()) |line| {
|
||||||
|
if (line.len == 0) continue;
|
||||||
|
const op = mem.indexOfAny(u8, line, "-=") orelse unreachable;
|
||||||
|
const label = line[0..op];
|
||||||
|
const label_hash = hash(label);
|
||||||
|
|
||||||
|
// Split init instead of using orelse because references.
|
||||||
|
if (boxes[label_hash] == null) {
|
||||||
|
boxes[label_hash] = std.StringArrayHashMap(u8).init(alloc);
|
||||||
|
}
|
||||||
|
var box = &(boxes[label_hash] orelse unreachable);
|
||||||
|
|
||||||
|
switch (line[op]) {
|
||||||
|
'-' => _ = box.orderedRemove(label),
|
||||||
|
'=' => {
|
||||||
|
const focus = try std.fmt.parseInt(u8, line[op + 1 ..], 10);
|
||||||
|
try box.put(label, focus);
|
||||||
|
},
|
||||||
|
else => unreachable,
|
||||||
|
}
|
||||||
|
|
||||||
|
// std.debug.print("{s}\n", .{ line });
|
||||||
|
// for (boxes, 0..) |bx, n| {
|
||||||
|
// if (bx) |b| {
|
||||||
|
// std.debug.print("box {}: {any} = {any}\n", .{ n, b.keys(), b.values() });
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// std.debug.print("---\n", .{});
|
||||||
|
}
|
||||||
|
|
||||||
|
var focus: usize = 0;
|
||||||
|
for (boxes, 1..) |maybe_box, box_n| {
|
||||||
|
var box = maybe_box orelse continue;
|
||||||
|
var box_it = box.iterator();
|
||||||
|
var lens_n: usize = 1;
|
||||||
|
while (box_it.next()) |entry| {
|
||||||
|
const label = entry.key_ptr.*;
|
||||||
|
_ = label;
|
||||||
|
const focal_len = entry.value_ptr.*;
|
||||||
|
const focus_power = box_n * lens_n * focal_len;
|
||||||
|
// std.debug.print("{s}: box {} * slot {} * focal length {} = {}\n", .{ label, box_n, lens_n, focal_len, focus_power });
|
||||||
|
focus += focus_power;
|
||||||
|
lens_n += 1;
|
||||||
|
}
|
||||||
|
box.deinit();
|
||||||
|
}
|
||||||
|
|
||||||
|
return .{ .a = hash_sum, .b = focus };
|
||||||
|
}
|
||||||
|
|
||||||
|
test "sample hash" {
|
||||||
|
try std.testing.expectEqual(@as(usize, 52), hash("HASH"));
|
||||||
|
}
|
||||||
|
|
||||||
|
test "silver" {
|
||||||
|
const input =
|
||||||
|
\\rn=1,cm-,qp=3,cm=2,qp-,pc=4,ot=9,ab=5,pc-,pc=6,ot=7
|
||||||
|
;
|
||||||
|
const sln = try solve(std.testing.allocator, input);
|
||||||
|
try std.testing.expectEqual(@as(usize, 1320), sln.a);
|
||||||
|
}
|
||||||
|
|
||||||
|
test "gold" {
|
||||||
|
const input =
|
||||||
|
\\rn=1,cm-,qp=3,cm=2,qp-,pc=4,ot=9,ab=5,pc-,pc=6,ot=7
|
||||||
|
;
|
||||||
|
const sln = try solve(std.testing.allocator, input);
|
||||||
|
try std.testing.expectEqual(@as(usize, 145), sln.b);
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user