diff --git a/day21.py b/day21.py new file mode 100644 index 0000000..d53cb6e --- /dev/null +++ b/day21.py @@ -0,0 +1,86 @@ +import collections + + +def read_food(): + with open('day21/input') as reader: + return reader.readlines() + + +food_as_text = read_food() + +food = [] +for f in food_as_text: + ingredients, allergens = f[:-1].split(' (contains ') + food.append((ingredients.split(' '), allergens[:-1].split(', '))) + + +def get_allergen_possibilities(food): + allergen_possibilities = {} + for ingredients, allergens in food: + for a in allergens: + if a not in allergen_possibilities.keys(): + allergen_possibilities[a] = set(ingredients) + else: + allergen_possibilities[a] = allergen_possibilities[a].intersection(set(ingredients)) + return allergen_possibilities + + +def get_all_ingredients_with_possible(allergen_possibilities): + all_ingredients_with_possible = set() + for i in allergen_possibilities.values(): + all_ingredients_with_possible = all_ingredients_with_possible.union(i) + return all_ingredients_with_possible + + +def get_all_ingredients(food): + all_ingredients = set() + for ingredients, allergens in food: + all_ingredients = all_ingredients.union(ingredients) + return all_ingredients + + +def count_no_allergens(food, no_allergen): + c = 0 + for ingredients, allergens in food: + for i in ingredients: + if i in no_allergen: + c += 1 + return c + + +def find_allergens(allergen_possibilities): + defined_allergens = {} + while True: + found_key, found_value = next((key, value) for key, value in allergen_possibilities.items() if len(value) == 1) + ingredient_defined = list(found_value)[0] + + defined_allergens[found_key] = ingredient_defined + + del allergen_possibilities[found_key] + for allergen in allergen_possibilities.keys(): + if ingredient_defined in allergen_possibilities[allergen]: + allergen_possibilities[allergen].remove(ingredient_defined) + + if not allergen_possibilities: + break + + return defined_allergens + + +allergen_possibilities = get_allergen_possibilities(food) +all_ingredients_with_possible = get_all_ingredients_with_possible(allergen_possibilities) +all_ingredients = get_all_ingredients(food) + +no_allergen = all_ingredients.difference(all_ingredients_with_possible) + +res = count_no_allergens(food, no_allergen) + +print(res) + +defined_allergens = find_allergens(allergen_possibilities) + +ordered_by_insertion = collections.OrderedDict(sorted(defined_allergens.items())) + +canonical_dangerous_ingredient_list = ','.join([v for v in ordered_by_insertion.values()]) + +print(canonical_dangerous_ingredient_list)