diff --git a/2022/day05_supply_stacks.py b/2022/day05_supply_stacks.py index 50bd659..2a388de 100644 --- a/2022/day05_supply_stacks.py +++ b/2022/day05_supply_stacks.py @@ -1,5 +1,6 @@ from __future__ import annotations +import copy import dataclasses import re @@ -9,14 +10,14 @@ def main(filename: str, expected_part_1: str = None, expected_part_2: str = None with open(filename) as f: data = f.read().rstrip().split("\n\n") - data = parse_data(data) - solution_part_1 = solve_part_1(data) + data_1, data_2 = parse_data(data) + solution_part_1 = solve_part_1(data_1) print(f"1. Found {solution_part_1}") if expected_part_1: assert expected_part_1 == solution_part_1 - solution_part_2 = solve_part_2(data) + solution_part_2 = solve_part_2(data_2) print(f"2. Found {solution_part_2}") if expected_part_2: assert expected_part_2 == solution_part_2 @@ -48,14 +49,15 @@ class Game: stacks: list[list[str]] instructions: list[Instruction] + def __str__(self): + return "\n".join(map(str, self.stacks)) + def play_instructions(self) -> None: for instruction in self.instructions: self.execute(instruction) def execute(self, instruction: Instruction) -> None: - for _ in range(instruction.quantity): - item = self.stacks[instruction.source].pop() - self.stacks[instruction.destination].append(item) + raise NotImplementedError() def message(self) -> str: msg = "" @@ -64,14 +66,29 @@ class Game: msg += stack[-1] return msg - def __str__(self): - return "\n".join(map(str, self.stacks)) + +class Game1(Game): + def execute(self, instruction: Instruction) -> None: + for _ in range(instruction.quantity): + item = self.stacks[instruction.source].pop() + self.stacks[instruction.destination].append(item) + + +class Game2(Game): + def execute(self, instruction: Instruction) -> None: + temp_stack = [] + for _ in range(instruction.quantity): + item = self.stacks[instruction.source].pop() + temp_stack.append(item) + for _ in range(instruction.quantity): + item = temp_stack.pop() + self.stacks[instruction.destination].append(item) DataType = Game -def parse_data(data: list[str]) -> DataType: +def parse_data(data: list[str]) -> tuple[DataType, DataType]: stacks, instructions = data parsed_instructions = [] for instruction in instructions.split("\n"): @@ -88,7 +105,9 @@ def parse_data(data: list[str]) -> DataType: break stack.append(char) parsed_stacks.append(stack) - return Game(parsed_stacks, parsed_instructions) + return Game1( + copy.deepcopy(parsed_stacks), copy.deepcopy(parsed_instructions) + ), Game2(copy.deepcopy(parsed_stacks), copy.deepcopy(parsed_instructions)) def solve_part_1(data: DataType) -> str: @@ -97,9 +116,10 @@ def solve_part_1(data: DataType) -> str: def solve_part_2(data: DataType) -> str: - return "0" + data.play_instructions() + return data.message() if __name__ == "__main__": - main("inputs/day05-test1", expected_part_1="CMZ") - main("inputs/day05") + main("inputs/day05-test1", expected_part_1="CMZ", expected_part_2="MCD") + main("inputs/day05", expected_part_1="BWNCQRMDB", expected_part_2="NHWZCBNBF")