application/octet-stream
•
2.06 KB
•
66 lines
#!/usr/bin/env nujel
[defun polymer/read [line]
[def eles @[]]
[def pairs @[]]
[for [i 0 [string/length line]]
[tree/++ eles [str->sym [substr line i [+ i 1]]]]
[when [< i [- [string/length line] 1]]
[tree/++ pairs [str->sym [substr line i [+ i 2]]]]]]
@[:pairs pairs :eles eles :combinations '[]]
]
[defun combination/parse [recipe last-recipe]
[def source [str->sym [car recipe]]]
[def new [str->sym [cadr recipe]]]
[def new-α [str->sym [cat [substr [car recipe] 0 1] [cadr recipe]]]]
[def new-β [str->sym [cat [cadr recipe] [substr [car recipe] 1 2]]]]
[\ [α Ω]
[def count [int [[α :pairs] source]]]
[tree/+= [Ω :eles] new count]
[tree/+= [Ω :pairs] source [- count]]
[tree/+= [Ω :pairs] new-α count]
[tree/+= [Ω :pairs] new-β count]
[if last-recipe [last-recipe α Ω] Ω]]
]
[defun combination/add [state recipe]
[tree/set! state :combinations [combination/parse recipe [state :combinations]]]
]
[defun combinations/read [state lines]
[for-each [\ [line] [combination/add state [split line " -> "]]] lines]
state
]
[defun state/read [fn]
[def input-raw [split [file/read fn] "\n"]]
[def state [polymer/read [car input-raw]]]
[combinations/read state [cddr input-raw]]
]
[defun state/dup [α]
@[:combinations [α :combinations] :pairs [tree/dup [α :pairs]] :eles [tree/dup [α :eles]]]
]
[defun state/run/once [α]
[[α :combinations] α [state/dup α]]
]
[defun state/run/many [α steps]
[if [<= steps 0] α [state/run/many [state/run/once α] [- steps 1]]]
]
[defun result [state]
[- [apply max [tree/values [state :eles]]]
[apply min [tree/values [state :eles]]]]
]
[def state [state/read "tests/day14.input"]]
[def p1-state [state/run/many state 10]]
[def res-p1 [result p1-state]]
[when [!= res-p1 2010]
[throw [list :wrong-result "Wrong result" res-p1]]]
[def res-p2 [result [state/run/many p1-state 30]]]
[when [!= res-p2 2437698971143]
[throw [list :wrong-result "Wrong result" res-p2]]]