alexandrajay2002

Advent of Code 2024 day 19 part 2

Dec 19th, 2024
54
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 1.46 KB | Source Code | 0 0
  1. from operator import itemgetter
  2. from collections import defaultdict
  3. from argparse import ArgumentParser, FileType
  4.  
  5.  
  6. def parse_towels(line):
  7.     return sorted(((towel, len(towel)) for towel in line.split(', ')),
  8.                   key=itemgetter(1), reverse=True)
  9.  
  10.  
  11. def parse_patterns(src):
  12.     return [line for line in src.splitlines() if line != '']
  13.  
  14.  
  15. def parse(src):
  16.     towels, patterns = src.split('\n\n', 1)
  17.     return parse_towels(towels), parse_patterns(patterns)
  18.  
  19.  
  20. def possible(pattern, towels):
  21.     todo = {pattern, }
  22.     counts = defaultdict(int, {pattern: 1})
  23.  
  24.     while len(todo) > 0:
  25.         part = max(todo, key=len)
  26.         todo.remove(part)
  27.         for towel, towel_len in towels:
  28.             if part[:towel_len] == towel:
  29.                 new_part = part[towel_len:]
  30.                 counts[new_part] += counts[part]
  31.  
  32.                 if new_part != '':
  33.                     todo.add(new_part)
  34.  
  35.     return counts['']
  36.  
  37.  
  38. def main(towels, patterns, verbose):
  39.     total = 0
  40.     for pattern in patterns:
  41.         result = possible(pattern, towels)
  42.         if verbose:
  43.             print(f'{pattern} can be made in {result} ways')
  44.         total += result
  45.  
  46.     return total
  47.  
  48.  
  49. arg_parser = ArgumentParser()
  50. arg_parser.add_argument('src', type=FileType('r'))
  51. arg_parser.add_argument('-v', '--verbose', action='store_true')
  52.  
  53. if __name__ == '__main__':
  54.     args = arg_parser.parse_args()
  55.     print(main(*parse(args.src.read()), args.verbose))
  56.  
Advertisement
Add Comment
Please, Sign In to add comment