import sys from collections import Counter from typing import Literal def generator_rating( values: list[str], most_common: bool, default: Literal["0", "1"] ) -> str: index = 0 most_common_idx = 0 if most_common else 1 while len(values) > 1: cnt = Counter(value[index] for value in values) bit = cnt.most_common(2)[most_common_idx][0] if cnt["0"] == cnt["1"]: bit = default values = [value for value in values if value[index] == bit] index += 1 return values[0] lines = sys.stdin.read().splitlines() # part 1 most_and_least_common = [ tuple(Counter(line[col] for line in lines).most_common(2)[m][0] for m in range(2)) for col in range(len(lines[0])) ] gamma_rate = int("".join(most for most, _ in most_and_least_common), base=2) epsilon_rate = int("".join(least for _, least in most_and_least_common), base=2) print(f"answer 1 is {gamma_rate * epsilon_rate}") # part 2 oxygen_generator_rating = int(generator_rating(lines, True, "1"), base=2) co2_scrubber_rating = int(generator_rating(lines, False, "0"), base=2) answer_2 = oxygen_generator_rating * co2_scrubber_rating print(f"answer 2 is {answer_2}")