diff options
| author | mryouse | 2023-06-03 20:22:18 +0000 |
|---|---|---|
| committer | mryouse | 2023-06-03 20:22:18 +0000 |
| commit | 7b7bf727da3250907284368b98b0083a4b4e2386 (patch) | |
| tree | 34802caea5181dc0fb97992746ab99b080448418 /aoc/2021/day04/part01.neb | |
initial commit
Diffstat (limited to 'aoc/2021/day04/part01.neb')
| -rw-r--r-- | aoc/2021/day04/part01.neb | 101 |
1 files changed, 101 insertions, 0 deletions
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))) |
