2 Commits

Author SHA1 Message Date
98983f622c It looks nice, not what I expected 2024-12-14 09:18:36 +01:00
4a7305d7eb Implement 2024 day 14 2024-12-14 09:11:16 +01:00
3 changed files with 99 additions and 0 deletions

View File

@@ -0,0 +1,80 @@
import itertools
import math
import re
import sys
import numpy
from . import SeparateRunner
NASTY_REGEX = re.compile(r"p=(-?\d+),(-?\d+) v=(-?\d+),(-?\d+)")
class DayRunner(SeparateRunner):
@classmethod
def part1(cls, input: str, width: int = 101, height: int = 103) -> int:
points = NASTY_REGEX.findall(input)
quadrants = [0] * 4
x_middle = width // 2
y_middle = height // 2
for point in points:
x, y, dx, dy = map(int, point)
rx = ((x + dx * 100) % width + width) % width
ry = ((y + dy * 100) % height + height) % height
match rx:
case _ if rx < x_middle:
xq = 0
case _ if rx > x_middle:
xq = 1
case _:
continue
match ry:
case _ if ry < y_middle:
yq = 0
case _ if ry > y_middle:
yq = 1
case _:
continue
quadrants[2 * yq + xq] += 1
return math.prod(quadrants)
@classmethod
def part2(cls, input: str) -> int:
width = 101
height = 103
points = NASTY_REGEX.findall(input)
points_fast = numpy.array([list(map(int, point)) for point in points])
positions = points_fast[:, 0:2]
velocities = points_fast[:, 2:]
target = len(velocities)
# Assumption: when the easter egg happens, no robots overlap, and this is the
# only time this happens. There is no reason this should work but it does.
mod_base = numpy.array([width, height])
for i in itertools.count(1):
positions += velocities
positions %= mod_base
positions += mod_base
positions %= mod_base
if len(numpy.unique(positions, axis=0)) == target:
grid = [[" "] * width for _ in range(height)]
for x, y in positions:
grid[y][x] = "#"
tree = "\n".join(map((lambda x: "".join(x)), grid))
print(tree, file=sys.stderr)
return i

12
2024/tests/samples/14.txt Normal file
View File

@@ -0,0 +1,12 @@
p=0,4 v=3,-3
p=6,3 v=-1,-3
p=10,3 v=-1,2
p=2,0 v=2,-1
p=0,0 v=1,3
p=3,0 v=-2,-2
p=7,6 v=-1,-3
p=3,0 v=-1,-2
p=9,3 v=2,3
p=7,3 v=-1,2
p=2,4 v=2,-3
p=9,5 v=-3,-3

7
2024/tests/test_day14.py Normal file
View File

@@ -0,0 +1,7 @@
from aoc.days.day14 import DayRunner
from . import get_data
def test_sample_part1() -> None:
assert DayRunner.part1(get_data(14), width=11, height=7) == 12