summaryrefslogtreecommitdiffstats
path: root/day21/__init__.py
diff options
context:
space:
mode:
authorGravatar Tom van der Lee <t0m.vd.l33@gmail.com>2022-12-28 13:31:29 +0100
committerGravatar Tom van der Lee <t0m.vd.l33@gmail.com>2022-12-28 13:31:29 +0100
commit1644c904de1544f788a8e88aa6c52bcd6a625b93 (patch)
tree9818613092865c6ca527329477f350731cc2d4c6 /day21/__init__.py
parentc22544594e251613a5dbf6c4ee505716867e55e6 (diff)
download2022-1644c904de1544f788a8e88aa6c52bcd6a625b93.tar.gz
2022-1644c904de1544f788a8e88aa6c52bcd6a625b93.tar.bz2
2022-1644c904de1544f788a8e88aa6c52bcd6a625b93.zip
Day 21 [WIP]main
Diffstat (limited to 'day21/__init__.py')
-rw-r--r--day21/__init__.py122
1 files changed, 122 insertions, 0 deletions
diff --git a/day21/__init__.py b/day21/__init__.py
new file mode 100644
index 0000000..23fd520
--- /dev/null
+++ b/day21/__init__.py
@@ -0,0 +1,122 @@
1# -*- coding: utf-8 -*-
2from abc import ABC
3from typing import Dict, Union, Iterator, Type, Callable, List
4from operator import add, sub, mul, truediv, eq, floordiv
5
6from aoc import BaseAssignment
7from aoc.decorators import list_input
8from aoc.mixins import AStarMixin
9
10
11class MonkeyActivity:
12 def __init__(self, name: str, monkeys: Dict[str, "MonkeyActivity"]):
13 self.name = name
14 self.monkeys = monkeys
15 self.monkeys[name] = self
16
17 def __repr__(self):
18 return f"{self.name}"
19
20 @property
21 def value(self) -> int:
22 raise NotImplementedError()
23
24
25class Yell(MonkeyActivity):
26 def __init__(self, value: str, *args, **kwargs):
27 super().__init__(*args, **kwargs)
28
29 self._value = int(value)
30
31 @property
32 def value(self) -> int:
33 return self._value
34
35
36class Operate(MonkeyActivity):
37 def __init__(self, a: str, b: str, operator: str, *args, **kwargs):
38 super().__init__(*args, **kwargs)
39
40 self.operator = operator
41 self._a = a
42 self._b = b
43 self._operator = {
44 "+": add,
45 "-": sub,
46 "*": mul,
47 "/": truediv,
48 }[operator]
49
50 @property
51 def a(self) -> MonkeyActivity:
52 return self.monkeys[self._a]
53
54 @property
55 def b(self) -> MonkeyActivity:
56 return self.monkeys[self._b]
57
58 @property
59 def value(self) -> int:
60 return int(self._operator(self.a.value, self.b.value))
61
62
63class Assignment(BaseAssignment[int, MonkeyActivity], ABC):
64 monkeys = {}
65
66 def parse_item(self, item: str) -> MonkeyActivity:
67 name, activity = item.split(": ")
68 activity = activity.split(" ")
69
70 if len(activity) == 1:
71 return Yell(*activity, name, self.monkeys)
72
73 a, operator, b = activity
74
75 return Operate(a, b, operator, name, self.monkeys)
76
77
78class AssignmentOne(Assignment):
79 example_result = 152
80
81 @list_input
82 def run(self, _: List[MonkeyActivity]) -> int:
83 return self.monkeys["root"].value
84
85
86class AssignmentTwo(Assignment, AStarMixin[MonkeyActivity]):
87 example_result = 301
88
89 @staticmethod
90 def neighbours(node: MonkeyActivity):
91 if isinstance(node, Operate):
92 yield node.a
93 yield node.b
94
95 @list_input
96 def run(self, _: List[MonkeyActivity]) -> int:
97 root = self.monkeys["root"]
98 humn = self.monkeys["humn"]
99 humn._value = 0
100
101 path = self.a_star(
102 root,
103 lambda n, _: n is humn,
104 self.neighbours,
105 )
106
107 for item in path:
108 if isinstance(item, Yell):
109 break
110
111 item: Operate = item
112 reverse_operator = {
113 "+": sub,
114 "-": add,
115 "*": floordiv,
116 "/": mul,
117 }[item.operator]
118
119 humn._value = reverse_operator(item.b.value, item.a.value)
120 pass
121
122 return humn._value