Advertisement
petrlos

AoC 2024/21

Jan 5th, 2025
79
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 2.15 KB | None | 0 0
  1. #Advent of Code 2024: Day 21
  2. from icecream import ic
  3. from collections import deque
  4. from itertools import product
  5.  
  6. def bfs(first, second, keyboard):
  7.     result = []
  8.     queue = deque([[keyboard[first], "", set()]])
  9.     min_length = 100
  10.  
  11.     while queue:
  12.         (r, c), path, seen = queue.popleft()
  13.         if first == second: return ["A"]
  14.         seen.add((r,c))
  15.         for r, c, p in [(r-1, c, "^"), (r, c-1, "<"), (r+1, c, "v"), (r, c+1, ">")]:
  16.             if (r, c) not in keyboard.values(): continue
  17.             if (r, c) in seen: continue
  18.             if keyboard[second] == (r,c):
  19.                 if min_length >= len(path + p):
  20.                     min_length = len(path + p + "A")
  21.                     result.append(path + p + "A")
  22.             else:
  23.                 queue.append([(r, c), path + p, seen])
  24.     return result
  25.  
  26. def generate_paths(keyb):
  27.     #generate all possible paths between all buttons on a keyboard
  28.     keyboard = {}
  29.     paths = dict()
  30.     for r, line in enumerate(keyb):
  31.         for c, char in enumerate(line):
  32.             if char == None: continue
  33.             keyboard[char] = (r,c)
  34.     for first in keyboard.keys():
  35.         for second in keyboard.keys():
  36.             paths[(first, second)] = bfs(first, second, keyboard)
  37.     return paths
  38.  
  39. def solve_path(path, path_keyboard):
  40.     result = []
  41.     for first, second in zip("A" + path, path):
  42.         result.append(path_keyboard[(first, second)])
  43.     paths = ["".join(map(str, combo)) for combo in list(product(*result))]
  44.     length = min(len(s) for s in paths)
  45.     return [s for s in paths if len(s) == length]
  46.  
  47. #MAIN
  48. with open("test.txt") as file:
  49.     lines = file.read().splitlines()
  50.  
  51. #generate all possible paths between all buttons on both keyboards
  52. paths_nums = generate_paths([["7", "8", "9"], ["4","5","6"], ["1", "2" ,"3"], [None, "0","A"]])
  53. paths_arrows = generate_paths([[None, "^", "A"], ["<", "v", ">"]])
  54.  
  55. ic(paths_nums)
  56.  
  57.  
  58. for num in lines:
  59.     paths = solve_path(num, paths_nums)
  60.     for path in paths:
  61.         second = solve_path(path, paths_arrows)
  62.     for path in second:
  63.         third = solve_path(path, paths_arrows)
  64.     print(num, len(third[0]))
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement