From 8b9919f784f93bdca7335354e7eea782b397fe0c Mon Sep 17 00:00:00 2001 From: Tom van der Lee Date: Mon, 5 Dec 2022 10:26:45 +0100 Subject: Day 5 --- day5/__init__.py | 108 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 108 insertions(+) create mode 100644 day5/__init__.py (limited to 'day5/__init__.py') diff --git a/day5/__init__.py b/day5/__init__.py new file mode 100644 index 0000000..a9aaba5 --- /dev/null +++ b/day5/__init__.py @@ -0,0 +1,108 @@ +# -*- coding: utf-8 -*- +import re +from abc import ABC +from typing import Iterator, Any, TypedDict, Tuple, List +from queue import LifoQueue + +from aoc import BaseAssignment + +move_regex = re.compile("^move (?P\d+) from (?P\d+) to (?P\d+)$") + + +class Move(TypedDict): + amount: int + start: int + end: int + + +class Assignment(BaseAssignment, ABC): + def parse_move(self, move: str) -> Move: + match = move_regex.match(move) + if match: + move = match.groupdict() + return Move( + amount=int(move["amount"]), + start=int(move["start"]), + end=int(move["end"]), + ) + + def parse_stacks(self, string_stacks: List[str]) -> List[LifoQueue]: + stacks = [] + columns = string_stacks.pop().replace(" ", "") + + for i in range(len(columns)): + stacks.append(LifoQueue()) + + for line in reversed(string_stacks): + for index, stack in enumerate(stacks): + item_index = (index * 4) + 1 + + try: + item = line[item_index] + if item != " ": + stack.put(item) + except IndexError: + pass + + return stacks + + def parse_input(self, input: Iterator) -> Tuple[List[LifoQueue], List[Move]]: + parsing_stacks = True + tmp_stacks = [] + stacks = [] + moves = [] + + for line in input: + if line == "": + parsing_stacks = False + stacks = self.parse_stacks(tmp_stacks) + continue + + if parsing_stacks: + tmp_stacks.append(line) + else: + moves.append(self.parse_move(line)) + + return stacks, moves + + def execute_moves(self, stacks: List[LifoQueue], moves: List[Move]): + raise NotImplementedError() + + def run(self, input: Iterator) -> Any: + stacks, moves = self.parse_input(input) + + self.execute_moves(stacks, moves) + + return "".join([stack.get() for stack in stacks]) + + +class AssignmentOne(Assignment): + example_result = "CMZ" + + def execute_moves(self, stacks: List[LifoQueue], moves: List[Move]): + for move in moves: + start = stacks[move["start"] - 1] + end = stacks[move["end"] - 1] + + for _ in range(move["amount"]): + end.put(start.get()) + + return stacks + + +class AssignmentTwo(Assignment): + example_result = "MCD" + + def execute_moves(self, stacks: List[LifoQueue], moves: List[Move]): + for move in moves: + start = stacks[move["start"] - 1] + end = stacks[move["end"] - 1] + + tmp_stack = LifoQueue() + for _ in range(move["amount"]): + tmp_stack.put(start.get()) + + while not tmp_stack.empty(): + end.put(tmp_stack.get()) + + return stacks -- cgit v1.2.3