aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorOrfeas <38209077+0xfea5@users.noreply.github.com>2023-12-19 04:21:10 +0200
committerOrfeas <38209077+0xfea5@users.noreply.github.com>2025-10-28 23:20:45 +0200
commit6c8982230b9402cc2e705a70e5dcc61b0b9187ea (patch)
tree44a756cfe90bcf10cfa2c07bd2c7b69900da7122
parentday17 (diff)
downloadaoc23-6c8982230b9402cc2e705a70e5dcc61b0b9187ea.tar.gz
aoc23-6c8982230b9402cc2e705a70e5dcc61b0b9187ea.zip
day18
-rw-r--r--day18/example.txt14
-rw-r--r--day18/solution.zig123
2 files changed, 137 insertions, 0 deletions
diff --git a/day18/example.txt b/day18/example.txt
new file mode 100644
index 0000000..fc7612e
--- /dev/null
+++ b/day18/example.txt
@@ -0,0 +1,14 @@
1R 6 (#70c710)
2D 5 (#0dc571)
3L 2 (#5713f0)
4D 2 (#d2c081)
5R 2 (#59c680)
6D 2 (#411b91)
7L 5 (#8ceee2)
8U 2 (#caa173)
9L 1 (#1b58a2)
10U 2 (#caa171)
11R 2 (#7807d2)
12U 3 (#a77fa3)
13L 2 (#015232)
14U 2 (#7a21e3)
diff --git a/day18/solution.zig b/day18/solution.zig
new file mode 100644
index 0000000..11da2a1
--- /dev/null
+++ b/day18/solution.zig
@@ -0,0 +1,123 @@
1const std = @import("std");
2const print = std.debug.print;
3const assert = std.debug.assert;
4const ArrayList = std.ArrayList;
5const HashMap = std.HashMap;
6const mem = std.mem;
7
8const fin = mem.trim(u8, @embedFile("./example.txt"), &std.ascii.whitespace);
9var gpa = std.heap.GeneralPurposeAllocator(.{}){};
10const allocator = gpa.allocator();
11
12const Direction = [_][2]u64{
13 [_]i64{ -1, 0 },
14 [_]i64{ 0, 1 },
15 [_]i64{ 1, 0 },
16 [_]i64{ 0, -1 },
17};
18
19const Move = struct {
20 dir: usize,
21 dist: isize,
22 color: []const u8,
23};
24
25fn abs(a: i64, b: i64) u64 {
26 return @as(u64, @bitCast(@max(a, b) - @min(a, b)));
27}
28
29fn evaluate(moves: []const Move) !u64 {
30 var polygon = ArrayList([2]i64).init(allocator);
31 defer polygon.deinit();
32
33 var curr = [_]i64{ 0, 0 };
34 var bl: u64 = 0;
35
36 for (moves) |m| {
37 const next = switch (m.dir) {
38 'U' => .{
39 curr[0] - m.dist,
40 curr[1],
41 },
42 'R' => .{
43 curr[0],
44 curr[1] + m.dist,
45 },
46 'D' => .{
47 curr[0] + m.dist,
48 curr[1],
49 },
50 'L' => .{
51 curr[0],
52 curr[1] - m.dist,
53 },
54 else => unreachable,
55 };
56
57 bl += abs(curr[0], next[0]) + abs(curr[1], next[1]);
58 try polygon.append(next);
59 curr = next;
60 }
61
62 const points = polygon.items;
63 const nPoints = points.len;
64 var a2: i64 = 0;
65
66 for (points, 1..) |f, j| {
67 const s = points[j % nPoints];
68
69 a2 += f[0] * s[1] - f[1] * s[0];
70 }
71
72 const a: usize = @bitCast(@divTrunc(if (a2 > 0) a2 else -a2, 2));
73
74 return a + 1 + bl / 2;
75}
76
77pub fn solve(moves: []const Move) !void {
78 const part1 = try evaluate(moves);
79
80 print("{d}\n", .{part1});
81
82 var movespt2 = ArrayList(Move).init(allocator);
83 defer movespt2.deinit();
84
85 for (moves) |m| {
86 const dist = try std.fmt.parseInt(i64, m.color[0..5], 16);
87 const dir: u8 = switch (m.color[5]) {
88 '0' => 'R',
89 '1' => 'D',
90 '2' => 'L',
91 '3' => 'U',
92 else => unreachable,
93 };
94 try movespt2.append(Move{
95 .dist = dist,
96 .dir = dir,
97 .color = m.color,
98 });
99 }
100
101 const part2 = try evaluate(movespt2.items);
102
103 print("{d}\n", .{part2});
104}
105
106pub fn main() !void {
107 var splitLines = mem.splitScalar(u8, fin, '\n');
108 var moves = ArrayList(Move).init(allocator);
109
110 while (splitLines.next()) |line| {
111 var toks = mem.tokenizeAny(u8, line, " (#)");
112 const dir = toks.next().?[0];
113 const dist = try std.fmt.parseInt(i64, toks.next().?, 10);
114 const color = toks.next().?;
115
116 try moves.append(Move{
117 .dir = dir,
118 .dist = dist,
119 .color = color,
120 });
121 }
122 try solve(moves.items);
123}