Skip to content

Commit de060a5

Browse files
committed
Add day13 solution
1 parent 6a058eb commit de060a5

File tree

1 file changed

+109
-0
lines changed

1 file changed

+109
-0
lines changed

2024/13.livemd

Lines changed: 109 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,109 @@
1+
# Advent of Code 2024 - Day 13
2+
3+
```elixir
4+
Mix.install([
5+
{:req, "~> 0.5"},
6+
{:benchee, "~> 1.3"}
7+
])
8+
```
9+
10+
## Input
11+
12+
```elixir
13+
opts = [headers: [{"cookie", "session=#{System.fetch_env!("LB_AOC_SESSION")}"}]]
14+
puzzle_input = Req.get!("https://adventofcode.com/2024/day/13/input", opts).body
15+
```
16+
17+
```elixir
18+
puzzles =
19+
puzzle_input
20+
|> String.split("\n", trim: true)
21+
|> Enum.chunk_every(3)
22+
|> Enum.map(fn machine ->
23+
Enum.map(machine, fn row ->
24+
[[_patternx, x], [_patterny, y]] = Regex.scan(~r/[XY][+=](\d+)/, row)
25+
26+
{String.to_integer(x), String.to_integer(y)}
27+
end)
28+
end)
29+
```
30+
31+
## Helpers
32+
33+
```elixir
34+
defmodule ClawContraption do
35+
# ax * x + bx * y = px
36+
# ay * x + by * y = py
37+
def solve([{ax, ay}, {bx, by}, {px, py}]) do
38+
case ax * by - bx * ay do
39+
0 ->
40+
0
41+
42+
determinant ->
43+
num_x = px * by - bx * py
44+
num_y = ax * py - px * ay
45+
46+
if rem(num_x, determinant) == 0 and rem(num_y, determinant) == 0 do
47+
x = div(num_x, determinant)
48+
y = div(num_y, determinant)
49+
50+
{x, y}
51+
else
52+
0
53+
end
54+
end
55+
end
56+
57+
def calculate_cost({x, y}), do: x * 3 + y
58+
def calculate_cost(_result), do: 0
59+
end
60+
```
61+
62+
## Puzzle 1
63+
64+
```elixir
65+
puzzle_1 = fn ->
66+
Enum.map(puzzles, fn puzzle ->
67+
puzzle
68+
|> ClawContraption.solve()
69+
|> ClawContraption.calculate_cost()
70+
end)
71+
|> Enum.sum()
72+
end
73+
74+
puzzle_1.()
75+
```
76+
77+
## Puzzle 2
78+
79+
```elixir
80+
puzzle_2 = fn ->
81+
Enum.map(puzzles, fn puzzle ->
82+
[{ax, ay}, {bx, by}, {px, py}] = puzzle
83+
84+
[{ax, ay}, {bx, by}, {px + 10_000_000_000_000, py + 10_000_000_000_000}]
85+
|> ClawContraption.solve()
86+
|> ClawContraption.calculate_cost()
87+
end)
88+
|> Enum.sum()
89+
end
90+
91+
puzzle_2.()
92+
```
93+
94+
## Benchmarks
95+
96+
```elixir
97+
Benchee.run(
98+
%{
99+
"puzzle_1" => fn -> puzzle_1.() end,
100+
"puzzle_2" => fn -> puzzle_2.() end
101+
})
102+
```
103+
104+
| Name | ips | average | deviation | median | 99th % |
105+
| -------- | ------ | ---------- | --------- | ---------- | ---------- |
106+
| puzzle_1 | 9.53 K | 104.96 μs | ±12.40% | 104 μs | 117.92 μs |
107+
| puzzle_2 | 1.15 K | 869.68 μs | ±16.67% | 858.52 μs | 996.20 μs |
108+
109+
<!-- livebook:{"offset":2142,"stamp":{"token":"XCP.MtpXai4P8QGhTrDlue3MIahNrfQJqYb3dCKbU5YrogwpS7OnDUPcvim05h12CuqBiglI2XRg8VuVA6WrK6E4dEHvtyFk-WTxdu5V1QidgvZW7CkX9QY","version":2}} -->

0 commit comments

Comments
 (0)