diff --git a/day3/part1.py b/day3/part1.py new file mode 100755 index 0000000..3de9076 --- /dev/null +++ b/day3/part1.py @@ -0,0 +1,79 @@ +#!/usr/bin/env python3.11 +from dataclasses import dataclass +from typing import List +from pprint import pprint +import re + + +@dataclass +class Point: + x: int + y: int + + def __hash__(self): + return (self.x, self.y).__hash__() + + +@dataclass +class Number: + value: int + start: Point + end: Point + + def __hash__(self): + return (self.value, self.start, self.end).__hash__() + + +@dataclass +class Symbol(Point): + value: str + + +lines = [] +numbers: List[Number] = [] +symbols: List[Symbol] = [] + +with open("input.txt") as input: + lines = input.readlines() + +for line_no, line in enumerate(lines): + idx = 0 + while match := re.match("\.*(\d+|[^\.\d\n]).*", line[idx:]): + rec = match.group(1) + place = line[idx:].find(rec) + if re.match("\d+", rec): + number = Number( + value=int(rec), + start=Point(x=idx + place, y=line_no), + end=Point(x=idx + place + len(rec) - 1, y=line_no), + ) + numbers.append(number) + # print(number) + idx += place + len(rec) + else: + symbol = Symbol(value=rec, x=idx + place, y=line_no) + symbols.append(symbol) + # print(symbol) + idx += place + 1 + +# pprint(numbers) +# pprint(symbols) +selected_numbers = [] +for line_no in range(len(lines)): + for symbol in filter(lambda symbol: symbol.y == line_no, symbols): + # print(symbol.value, end="") + def selection(number: Number): + return ( + (number.start.y == line_no - 1 and number.start.x <= symbol.x + 1 and number.end.x >= symbol.x - 1) + or (number.start.y == line_no + 1 and number.start.x <= symbol.x + 1 and number.end.x >= symbol.x - 1) + or (number.end.x == symbol.x - 1 and number.end.y == line_no) + or (number.start.x == symbol.x + 1 and number.start.y == line_no) + ) + + sym_selected = list(filter(selection, numbers)) + selected_numbers += sym_selected + #print(symbol, sym_selected) +# print("") +selected_numbers = set(selected_numbers) +#pprint(selected_numbers) +print(sum(list(map(lambda number: number.value, selected_numbers)))) diff --git a/day3/part2.py b/day3/part2.py new file mode 100755 index 0000000..2ef8760 --- /dev/null +++ b/day3/part2.py @@ -0,0 +1,77 @@ +#!/usr/bin/env python3.11 +from dataclasses import dataclass +from typing import List +from pprint import pprint +import re + + +@dataclass +class Point: + x: int + y: int + + def __hash__(self): + return (self.x, self.y).__hash__() + + +@dataclass +class Number: + value: int + start: Point + end: Point + + def __hash__(self): + return (self.value, self.start, self.end).__hash__() + + +@dataclass +class Symbol(Point): + value: str + + +lines = [] +numbers: List[Number] = [] +symbols: List[Symbol] = [] + +with open("input.txt") as input: + lines = input.readlines() + +for line_no, line in enumerate(lines): + idx = 0 + while match := re.match("\.*(\d+|[^\.\d\n]).*", line[idx:]): + rec = match.group(1) + place = line[idx:].find(rec) + if re.match("\d+", rec): + number = Number( + value=int(rec), + start=Point(x=idx + place, y=line_no), + end=Point(x=idx + place + len(rec) - 1, y=line_no), + ) + numbers.append(number) + # print(number) + idx += place + len(rec) + else: + symbol = Symbol(value=rec, x=idx + place, y=line_no) + symbols.append(symbol) + # print(symbol) + idx += place + 1 + +# pprint(numbers) +# pprint(symbols) +the_sum = 0 +for line_no in range(len(lines)): + for symbol in filter(lambda symbol: symbol.y == line_no and symbol.value == "*", symbols): + # print(symbol.value, end="") + def selection(number: Number): + return ( + (number.start.y == line_no - 1 and number.start.x <= symbol.x + 1 and number.end.x >= symbol.x - 1) + or (number.start.y == line_no + 1 and number.start.x <= symbol.x + 1 and number.end.x >= symbol.x - 1) + or (number.end.x == symbol.x - 1 and number.end.y == line_no) + or (number.start.x == symbol.x + 1 and number.start.y == line_no) + ) + + selected = list(filter(selection, numbers)) + if len(selected) == 2: + # print(symbol, selected) + the_sum += selected[0].value * selected[1].value +print(the_sum)