|
3 | 3 | # Advent of Code 2015 Day 10
|
4 | 4 | #
|
5 | 5 |
|
6 |
| -from aoc import my_aocd |
| 6 | +import sys |
| 7 | + |
| 8 | +from aoc.common import InputData |
| 9 | +from aoc.common import SolutionBase |
7 | 10 | from aoc.common import spinner
|
8 | 11 |
|
| 12 | +Input = str |
| 13 | +Output1 = int |
| 14 | +Output2 = int |
9 | 15 |
|
10 |
| -def _look_and_say(string: str) -> str: |
11 |
| - result = "" |
12 |
| - i = 0 |
13 |
| - while i < len(string): |
14 |
| - digit = string[i] |
15 |
| - j = 0 |
16 |
| - while i+j < len(string) and string[i+j] == digit: |
17 |
| - j += 1 |
18 |
| - result += str(j) + digit |
19 |
| - i += j |
20 |
| - return result |
21 | 16 |
|
| 17 | +class Solution(SolutionBase[Input, Output1, Output2]): |
| 18 | + def parse_input(self, input_data: InputData) -> Input: |
| 19 | + return list(input_data)[0] |
22 | 20 |
|
23 |
| -def _look_and_say_iterations(string: str, iterations: int) -> str: |
24 |
| - for i in range(iterations): |
25 |
| - string = _look_and_say(string) |
26 |
| - spinner(i, iterations // 4) |
27 |
| - return string |
| 21 | + def look_and_say(self, string: str) -> str: |
| 22 | + result = "" |
| 23 | + i = 0 |
| 24 | + while i < len(string): |
| 25 | + digit = string[i] |
| 26 | + j = 0 |
| 27 | + while i + j < len(string) and string[i + j] == digit: |
| 28 | + j += 1 |
| 29 | + result += str(j) + digit |
| 30 | + i += j |
| 31 | + return result |
28 | 32 |
|
| 33 | + def solve(self, string: str, iterations: int) -> str: |
| 34 | + for i in range(iterations): |
| 35 | + string = self.look_and_say(string) |
| 36 | + spinner(i, iterations // 4) |
| 37 | + return string |
29 | 38 |
|
30 |
| -def part_1(inputs: tuple[str]) -> int: |
31 |
| - assert len(inputs) == 1 |
32 |
| - return len(_look_and_say_iterations(inputs[0], 40)) |
| 39 | + def part_1(self, input: Input) -> Output1: |
| 40 | + return len(self.solve(input, iterations=40)) |
33 | 41 |
|
| 42 | + def part_2(self, input: Input) -> Output2: |
| 43 | + return len(self.solve(input, iterations=50)) |
34 | 44 |
|
35 |
| -def part_2(inputs: tuple[str]) -> int: |
36 |
| - assert len(inputs) == 1 |
37 |
| - return len(_look_and_say_iterations(inputs[0], 50)) |
| 45 | + def samples(self) -> None: |
| 46 | + assert self.solve("1", iterations=5) == "312211" |
38 | 47 |
|
39 | 48 |
|
40 |
| -TEST = "1".splitlines() |
| 49 | +solution = Solution(2015, 10) |
41 | 50 |
|
42 | 51 |
|
43 | 52 | def main() -> None:
|
44 |
| - my_aocd.print_header(2015, 10) |
45 |
| - |
46 |
| - assert _look_and_say_iterations(TEST, 5) == "312211" |
47 |
| - |
48 |
| - inputs = my_aocd.get_input(2015, 10, 1) |
49 |
| - result1 = part_1(inputs) |
50 |
| - print(f"Part 1: {result1}") |
51 |
| - result2 = part_2(inputs) |
52 |
| - print(f"Part 2: {result2}") |
| 53 | + solution.run(sys.argv) |
53 | 54 |
|
54 | 55 |
|
55 |
| -if __name__ == '__main__': |
| 56 | +if __name__ == "__main__": |
56 | 57 | main()
|
0 commit comments