diff options
Diffstat (limited to 'aoc/2021/day04')
| -rw-r--r-- | aoc/2021/day04/input.txt | 19 | ||||
| -rw-r--r-- | aoc/2021/day04/part01.neb | 101 |
2 files changed, 120 insertions, 0 deletions
diff --git a/aoc/2021/day04/input.txt b/aoc/2021/day04/input.txt new file mode 100644 index 0000000..669a51d --- /dev/null +++ b/aoc/2021/day04/input.txt @@ -0,0 +1,19 @@ +7,4,9,5,11,17,23,2,0,14,21,24,10,16,13,6,15,25,12,22,18,20,8,19,3,26,1 + +22 13 17 11 0 + 8 2 23 4 24 +21 9 14 16 7 + 6 10 3 18 5 + 1 12 20 15 19 + + 3 15 0 2 22 + 9 18 13 17 5 +19 8 7 25 23 +20 11 10 24 4 +14 21 16 12 6 + +14 21 17 24 4 +10 16 15 9 19 +18 8 23 26 20 +22 11 13 6 5 + 2 0 12 3 7 diff --git a/aoc/2021/day04/part01.neb b/aoc/2021/day04/part01.neb new file mode 100644 index 0000000..49b4a7a --- /dev/null +++ b/aoc/2021/day04/part01.neb @@ -0,0 +1,101 @@ +;; https://adventofcode.com/2021/day/4 + +; good candidate for loop-acc +(func get-all-boards (inp) + (def ret (list)) + (for-count (/ (length inp) 5) + (redef ret (append ret + (get-board (slice inp (+ (* 5 (- _idx_ 1)) 1) 5))))) + ret) + +(func get-board (inp) + (map get-row inp)) + +; each row is a string of items +; separated by (potentially) several spaces +; return a list of just the strings +(func get-row (row) + (filter + (lambda (x) + (not (eq? "" x))) + (split row " "))) + + +(func process-boards (inp) + (def raw-boards + (filter + (lambda (x) (not (eq? "" x))) + inp)) + (get-all-boards raw-boards)) + +(def lines + (map strip + (read-lines "input.txt"))) + +(def moves (split (first lines) ",")) ; moves is the first line +(def boards (process-boards (rest lines))) + +; this is a helper to work with zippers +; probably good to have in the stdlib +(func unzip (lst idx) + (list + (reverse + (slice lst 1 idx)) + (slice lst (+ 1 idx)))) + +(func has-won-row (row) + (apply and row)) + +(func has-won (board moves) + (def checked (check-board board moves)) + (def winner #false) + + ; check rows + ; no break statement means we have to check everything, + ; even after a winner is found + ; can also use a while, but that would require more redefs + (for-each checked + (if (has-won-row _item_) + (redef winner #true))) + + ; no break here means we check columns even if we won on rows + + ; check columns + (for-count 5 + (if (has-won-row + (map + (lambda (x) (first (slice x _idx_ 1))) + checked)) + (redef winner #true))) + + winner) + + +(func check-board (board moves) + (func check-row (row) + (map + (lambda (x) + (in? x moves)) + row)) + (map check-row board)) + + +; how do we better iterate through this list? +; called/next would be perfect for a zipper +(def cur (list (list) moves)) ; init zip +(def winner #false) +(while (not winner) + (redef cur (unzip moves (+ 1 (length (first cur))))) + (print (->string cur)) + (print (->string + (map + (lambda (x) (has-won x (first cur))) + boards))) + ;(def checked (check-board (first boards) (first cur))) + ;(print (->string checked)) + (if (nil? (last cur)) + (redef winner #true)) + ) + +(print (->string moves)) +;(print (->string (unzip moves 2))) |
