Skip to content

Commit f10e573

Browse files
committed
Day 10
1 parent 08711c2 commit f10e573

File tree

1 file changed

+93
-1
lines changed

1 file changed

+93
-1
lines changed

aoc/2025/10/normal/10_normal.vn.py

Lines changed: 93 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,96 @@
11
# Advent of code Day 10
22
# https://adventofcode.com/2025/day/10
33
# 10/12/2025
4-
4+
5+
from functools import cache
6+
import heapq
7+
from collections import defaultdict
8+
from tqdm.auto import tqdm
9+
from collections import deque
10+
11+
def parse(buttons: str):
12+
buttons = buttons.strip().split()
13+
goal = tuple(map(lambda x: int(x == "#"),
14+
buttons[0][1:-1]))
15+
size = len(goal)
16+
req = tuple(map(int, buttons[-1][1:-1].split(",")))
17+
buttons = list(map(
18+
lambda s: tuple(map(int, s[1:-1].split(","))),
19+
buttons[1:-1]))
20+
for i in range(len(buttons)):
21+
r = [0 for _ in range(size)]
22+
for j in buttons[i]:
23+
r[j] = 1
24+
buttons[i] = tuple(r)
25+
return goal, buttons, req
26+
27+
28+
with open("input.txt") as file:
29+
inp = list(
30+
map(
31+
parse,
32+
file.readlines()
33+
)
34+
)
35+
36+
@cache
37+
def apply(button, state, mod=2):
38+
res = list(state)
39+
for i in range(len(res)):
40+
res[i] += button[i]
41+
if mod:
42+
res[i] %= mod
43+
return tuple(res)
44+
45+
res1, res2 = 0, 0
46+
for goal, buttons, req in tqdm(inp):
47+
n = len(goal)
48+
start = tuple(0 for _ in range(n))
49+
visited = defaultdict(bool)
50+
heap = [(0, start)]
51+
52+
while heap:
53+
presses, state = heapq.heappop(heap)
54+
55+
if visited[state]: continue
56+
visited[state] = True
57+
58+
if state == goal:
59+
res1 += presses
60+
break
61+
62+
for button in buttons:
63+
newState = apply(button, state)
64+
if visited[newState]: continue
65+
66+
heapq.heappush(
67+
heap,
68+
(presses+1, newState)
69+
)
70+
71+
from pulp import *
72+
73+
res2 = 0
74+
for goal, buttons, req in tqdm(inp):
75+
# Create integer variables (x[i] = times button i is pressed)
76+
x = [LpVariable(f"x{i}", 0, cat='Integer') for i in range(len(buttons))]
77+
78+
# Create optimization problem (minimization by default)
79+
prob = LpProblem()
80+
81+
# Objective: minimize total button presses
82+
prob += lpSum(x)
83+
84+
# Constraints: for each dimension, button presses must sum to goal
85+
for i in range(len(goal)):
86+
prob += lpSum(x[j] * buttons[j][i] for j in range(len(buttons))) == req[i]
87+
88+
# Solve with no output
89+
prob.solve(PULP_CBC_CMD(msg=0))
90+
91+
# If optimal solution found, add to result
92+
if prob.status == 1:
93+
res2 += int(value(prob.objective))
94+
95+
96+
print(res1, res2)

0 commit comments

Comments
 (0)