-
Notifications
You must be signed in to change notification settings - Fork 1
/
dayB.toit
76 lines (65 loc) · 2.1 KB
/
dayB.toit
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
import .resources
class Monkey:
items /List := []
// Too lazy to make a real expression parser, so we just recognize a few patterns and set these three fields.
op_add /int
op_mul /int
op_square /bool
modulus /int
true_index /int
false_index /int
count := 0
constructor --.items --.modulus --.true_index --.false_index --.op_add --.op_mul --.op_square:
operation value/int -> int:
result := (value + op_add) * op_mul
if op_square: result *= result
return result
process monkeys/List reduction/int --divide/bool -> none:
items.do: | worry/int |
count++
worry = operation worry
if divide:
worry /= 3
else:
worry %= reduction
if worry % modulus == 0:
monkeys[true_index].items.add worry
else:
monkeys[false_index].items.add worry
items = []
last_number str/string:
return int.parse str[(str.index_of --last " ") + 1..]
main:
run 20 --divide=true
run 10_000 --divide=false
run iterations/int --divide/bool:
monkeys ::= []
INPUTB.trim.split "\n\n":
lines := it.split "\n"
items := ((lines[1].split ": ")[1].split ", ").map: int.parse it
// Line 2 is the expression. Instead of an expression parser we just
// recognize the three patterns.
op_add := (lines[2].contains "+") ? (last_number lines[2]) : 0
op_mul := ?
op_square := ?
if lines[2].ends_with "old * old":
op_mul = 1
op_square = true
else:
op_mul = (lines[2].contains "*") ? (last_number lines[2]) : 1
op_square = false
modulus := last_number lines[3]
monkeys.add
Monkey
--items=items
--modulus=modulus
--true_index=last_number lines[4]
--false_index=last_number lines[5]
--op_add=op_add
--op_mul=op_mul
--op_square=op_square
reduction := monkeys.reduce --initial=1: | r monkey | r *= monkey.modulus
iterations.repeat:
monkeys.do: it.process monkeys reduction --divide=divide
most_active := (monkeys.sort: | a b | b.count - a.count)[..2]
print most_active[0].count * most_active[1].count