aboutsummaryrefslogtreecommitdiffstats
path: root/AoC2023/day09/solver.lisp
blob: d5153172e5fdfb086425d81e3272af3d7dbd16a8 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
;;03:39
(ql:quickload '(fiveam arrows transducers))
(defparameter eg-input "0 3 6 9 12 15
1 3 6 10 15 21
10 13 16 21 30 45")

(defun row-reducer (row)
  (loop for (a b) on row by #'cdr
        until (null b)
        collect (- b a)))

(defun terminal-p (row)
  (every #'zerop row))

(defun forward (row)
  (if (terminal-p row)
      0
      (+  (forward (row-reducer row)) (car (last row)))))

(defun backward (row)
  (if (terminal-p row)
      0
      (-  (car row)  (backward (row-reducer row)))))

(defun solver1 (lines)
  (arrows:->>
   lines
   (mapcar (lambda (line)
             (forward
              (mapcar #'parse-integer (uiop:split-string line)))))
   (apply #'+)))

(defun solver2 (lines)
  (arrows:->>
   lines
   (mapcar (lambda (line)
             (backward
              (mapcar #'parse-integer (uiop:split-string line)))))
   (apply #'+)))

(fiveam:test solutions
  (fiveam:is (= 114 (solver1 (uiop:split-string eg-input :separator '(#\Newline)))))
  (fiveam:is (= 2105961943 (solver1 (uiop:read-file-lines "input"))))

  (fiveam:is (= 2 (solver2 (uiop:split-string eg-input :separator '(#\Newline)))))
  (fiveam:is (= 1019 (solver2 (uiop:read-file-lines "input")))))