-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathday22.py
More file actions
89 lines (70 loc) · 2.47 KB
/
Copy pathday22.py
File metadata and controls
89 lines (70 loc) · 2.47 KB
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
77
78
79
80
81
82
83
84
85
86
87
88
89
filepath = "day22.txt"
import numpy as np
STOP_NUMBER = 2000
def read_file():
return (int(line.strip()) for line in open(filepath))
def mix_secret(given, secret):
return given ^ secret
def prune_secret(secret):
return secret % 16777216
def simulate_secrets(secret, how_many):
for i in range(how_many):
secret = prune_secret(mix_secret(secret * 64, secret))
secret = prune_secret(mix_secret(secret // 32, secret))
secret = prune_secret(mix_secret(secret * 2048, secret))
return secret
def simulate_diffs(secret, how_many):
last_numbers = []
for i in range(how_many):
last_numbers.append(int(str(secret)[-1]))
secret = prune_secret(mix_secret(secret * 64, secret))
secret = prune_secret(mix_secret(secret // 32, secret))
secret = prune_secret(mix_secret(secret * 2048, secret))
diffs = np.diff(last_numbers)
return last_numbers, diffs.tolist()
def generate_patterns(diffs):
patterns = []
for i in range(len(diffs) - 3):
patterns.append(tuple(diffs[i:i + 4]))
return patterns
# Find when a pattern first occurs for a buyer
def find_pattern_start(last_numbers, pattern):
diffs = np.diff(last_numbers)
for i in range(len(diffs) - 3):
if tuple(diffs[i:i + 4]) == pattern:
return i
return -1
def solve_part_i():
initials = read_file()
result = 0
for initial in initials:
secret = simulate_secrets(initial, STOP_NUMBER)
result += secret
print("Part I:", result)
def solve_part_ii():
initials = read_file()
max_bananas = 0
best_pattern = None
all_patterns = set()
all_last_numbers = []
for initial in initials:
last_numbers, diffs = simulate_diffs(initial, STOP_NUMBER)
all_last_numbers.append(last_numbers)
patterns = generate_patterns(diffs)
all_patterns.update(patterns)
print(f"{len(all_patterns)} patterns found")
for pattern in all_patterns:
total_bananas = 0
for last_numbers in all_last_numbers:
idx = find_pattern_start(last_numbers, pattern)
if idx != -1:
total_bananas += last_numbers[idx+4]
# Track the best pattern
if total_bananas > max_bananas:
max_bananas = total_bananas
best_pattern = pattern
print("Best max bananas so far...", max_bananas)
print("Best Patterns", best_pattern)
print("Part I:", max_bananas)
#solve_part_i()
solve_part_ii()