Advertisement
illuminati229

AoC 2022 Day 21

Dec 21st, 2022
1,053
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 3.12 KB | None | 0 0
  1. from time import time
  2. from z3 import *
  3.  
  4.  
  5. def timer_func(func):
  6.     # This function shows the execution time of
  7.     # the function object passed
  8.     def wrap_func(*args, **kwargs):
  9.         t1 = time()
  10.         result = func(*args, **kwargs)
  11.         t2 = time()
  12.         print(f'Function {func.__name__!r} executed in {(t2 - t1):.4f}s')
  13.         return result
  14.  
  15.     return wrap_func
  16.  
  17.  
  18. def monkey_eval(monkey_name, monkey_dict):
  19.     monkey_yell = monkey_dict[monkey_name]
  20.     if isinstance(monkey_yell, int):
  21.         return monkey_yell
  22.     else:
  23.         if monkey_yell[1] == '/':
  24.             return monkey_eval(monkey_yell[0], monkey_dict) / monkey_eval(monkey_yell[2], monkey_dict)
  25.         if monkey_yell[1] == '+':
  26.             return monkey_eval(monkey_yell[0], monkey_dict) + monkey_eval(monkey_yell[2], monkey_dict)
  27.         if monkey_yell[1] == '-':
  28.             return monkey_eval(monkey_yell[0], monkey_dict) - monkey_eval(monkey_yell[2], monkey_dict)
  29.         if monkey_yell[1] == '*':
  30.             return monkey_eval(monkey_yell[0], monkey_dict) * monkey_eval(monkey_yell[2], monkey_dict)
  31.         if monkey_yell[1] == '=':
  32.             return monkey_eval(monkey_yell[0], monkey_dict) == monkey_eval(monkey_yell[2], monkey_dict)
  33.  
  34.  
  35. @timer_func
  36. def day21(filepath, part2=False):
  37.     with open(filepath) as fin:
  38.         lines = fin.readlines()
  39.  
  40.     monkey_dict = {}
  41.     for line in lines:
  42.         monkey_name, monkey_yell = [x.strip() for x in line.split(':')]
  43.         monkey_yell = [x for x in monkey_yell.split()]
  44.         if len(monkey_yell) == 1:
  45.             monkey_yell = int(monkey_yell[0])
  46.         monkey_dict[monkey_name] = monkey_yell
  47.  
  48.     if not part2:
  49.         return int(monkey_eval('root', monkey_dict))
  50.     else:
  51.         vals = {}
  52.         s = Solver()
  53.         for key in monkey_dict.keys():
  54.             vals[key] = Real(key)
  55.         for key, val in monkey_dict.items():
  56.             if key == 'humn':
  57.                 # s.add(vals['humn'] < 3910938071093)
  58.                 continue
  59.             elif key == 'root':
  60.                 s.add(vals[val[0]] == vals[val[2]])
  61.             else:
  62.                 if isinstance(val, int):
  63.                     s.add(vals[key] == val)
  64.                 else:
  65.                     a, m, b = val
  66.                     if m == '+':
  67.                         s.add(vals[key] == (vals[a] + vals[b]))
  68.                     elif m == '-':
  69.                         s.add(vals[key] == (vals[a] - vals[b]))
  70.                     elif m == '*':
  71.                         s.add(vals[key] == (vals[a] * vals[b]))
  72.                     elif m == '/':
  73.                         s.add(vals[key] == (vals[a] / vals[b]))
  74.  
  75.         s.check()
  76.         m = s.model()
  77.         monkey_dict['humn'] = m[vals['humn']].as_long()
  78.         monkey_dict['root'][1] = '='
  79.         print(monkey_eval('root', monkey_dict))
  80.         return m[vals['humn']]
  81.  
  82.  
  83. def main():
  84.     assert day21('test21') == 152
  85.     print(f"Part 1: {day21('input21')}")
  86.  
  87.     assert day21('test21', True) == 301
  88.     print(f"Part 2: {day21('input21', True)}")
  89.     # print(f"Other test: {day21('othertest', True)}")
  90.  
  91.  
  92. if __name__ == '__main__':
  93.     main()
  94.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement