summaryrefslogtreecommitdiffstats
path: root/src/03.lisp
diff options
context:
space:
mode:
Diffstat (limited to 'src/03.lisp')
-rw-r--r--src/03.lisp45
1 files changed, 45 insertions, 0 deletions
diff --git a/src/03.lisp b/src/03.lisp
new file mode 100644
index 0000000..ae2f0bd
--- /dev/null
+++ b/src/03.lisp
@@ -0,0 +1,45 @@
+(load "~/quicklisp/setup.lisp")
+(ql:quickload "uiop")
+
+(defun get-file-lines (name)
+ (uiop:read-file-lines name))
+
+(defun parse-bin-char (x) (case x (#\1 1) (#\0 0)))
+
+;; Turn the input file into whatever form you will use for both parts
+;; (get-file-lines) and (get-file-string) will be useful
+(defun parse-input (input-file)
+ (mapcar (lambda (x) (mapcar #'parse-bin-char (coerce x 'list))) (get-file-lines input-file)))
+
+;; Loops through two item windows on input and counts each time the first is less than the second
+(defun partial (func &rest args1)
+ (lambda (&rest args2)
+ (apply func (append args1 args2))))
+
+(defun is-less (h l)
+ (mapcar (lambda (x) (if (< x h) 0 1)) l))
+
+(defun not-list (l)
+ (mapcar (lambda (x) (if (= x 0) 1 0)) l))
+
+(defun range (max &key (min 0) (step 1))
+ (loop :for n :from (- max 1) :above (- min 1) :by step
+ :collect n))
+
+(defun to-dec (l)
+ (apply #'+ (mapcar (lambda (a b) (* a (expt 2 b))) l (range (list-length l)))))
+
+(defun part-a (parsed-input)
+ (let* ((half-length (/ (list-length parsed-input) 2))
+ (l (is-less half-length (apply (partial #'mapcar #'+) parsed-input)))
+ (gamma (to-dec l))
+ (epsilon (to-dec (not-list l))))
+ (* epsilon gamma)))
+
+;; Similar to part a, but with four item windows, comparing the sum of the first 3 with the next 3
+(defun part-b (parsed-input)
+ (loop for (w x y z) on parsed-input until (null z) if (< (+ w x y) (+ x y z)) count w))
+
+(time (format t "part 1: ~a~%" (part-a (parse-input "../inputs/03.txt"))))
+;;(time (format t "part 1: ~a~%" (part-a (parse-input "test.txt"))))
+;;(time (format t "part 1: ~a~%" (part-b (parse-input "../inputs/01.txt"))))