Add solution for part 1 for day 11
This commit is contained in:
parent
cca98607c9
commit
8b1d2b2ce5
93
day11/day11.lisp
Normal file
93
day11/day11.lisp
Normal file
@ -0,0 +1,93 @@
|
|||||||
|
(ql:quickload :cl-ppcre)
|
||||||
|
|
||||||
|
(defclass monkey ()
|
||||||
|
((items
|
||||||
|
:accessor items
|
||||||
|
:initarg :items
|
||||||
|
:type list)
|
||||||
|
(op
|
||||||
|
:accessor op
|
||||||
|
:initarg :op
|
||||||
|
:type function)
|
||||||
|
(test
|
||||||
|
:accessor test
|
||||||
|
:initarg :test
|
||||||
|
:type function)
|
||||||
|
(actions
|
||||||
|
:accessor actions
|
||||||
|
:initarg :actions
|
||||||
|
:type list)
|
||||||
|
(inspections
|
||||||
|
:accessor inspections
|
||||||
|
:initarg :inspections
|
||||||
|
:type number)))
|
||||||
|
|
||||||
|
(defparameter *regexp* "Monkey (\\d+):\\n Starting items: ([0-9, ]+)\\n Operation: new = old ([\*\+]) (\\d+|\\w+)\\n Test: divisible by (\\d+)\\n If true: throw to monkey (\\d+)\\n If false: throw to monkey (\\d+)")
|
||||||
|
|
||||||
|
(defun str-to-list (str)
|
||||||
|
"Parses comma-separated string of integers in STR into a list of
|
||||||
|
integers."
|
||||||
|
(loop :for item :in (ppcre:split ", " str) :collect (parse-integer item)))
|
||||||
|
|
||||||
|
(defun make-op (operation operand)
|
||||||
|
"Returns a function matching the description given by STR."
|
||||||
|
(if (equal operand "old")
|
||||||
|
(if (equal operation "*")
|
||||||
|
(lambda (old) (* old old))
|
||||||
|
(lambda (old) (+ old old)))
|
||||||
|
(if (equal operation "*")
|
||||||
|
(lambda (old) (* old (parse-integer operand)))
|
||||||
|
(lambda (old) (+ old (parse-integer operand))))))
|
||||||
|
|
||||||
|
(defun make-test (str)
|
||||||
|
"Returns a function testing for divisibility by the number given in
|
||||||
|
STR."
|
||||||
|
(lambda (level) (zerop (mod level (parse-integer str)))))
|
||||||
|
|
||||||
|
(defun throw-item (monkeys src dest)
|
||||||
|
"Removes the first item held by the monkey at position SRC in MONKEYS
|
||||||
|
and adds it to the end of the items held by the monkey at position
|
||||||
|
DEST in MONKEYS."
|
||||||
|
(progn
|
||||||
|
(setf (items (nth dest monkeys))
|
||||||
|
(append (items (nth dest monkeys)) (list (car (items (nth src monkeys))))))
|
||||||
|
(setf (items (nth src monkeys))
|
||||||
|
(cdr (items (nth src monkeys))))))
|
||||||
|
|
||||||
|
(defun parse-input (input)
|
||||||
|
"Parses INPUT into a list of monkey objects."
|
||||||
|
(loop :for monkey
|
||||||
|
:in (ppcre:split "\\n\\n" (uiop:read-file-string input))
|
||||||
|
:collect
|
||||||
|
(ppcre:do-register-groups (id items operation operand test true false) (*regexp* monkey)
|
||||||
|
(return (make-instance 'monkey
|
||||||
|
:items (str-to-list items)
|
||||||
|
:op (make-op operation operand)
|
||||||
|
:test (make-test test)
|
||||||
|
:actions (list (parse-integer id) (parse-integer true)
|
||||||
|
(parse-integer id) (parse-integer false))
|
||||||
|
:inspections 0)))))
|
||||||
|
|
||||||
|
(defun run-round (monkeys div)
|
||||||
|
(let ((level 0))
|
||||||
|
(loop :for monkey :in monkeys :do
|
||||||
|
(loop :for item :in (items monkey) :do
|
||||||
|
(progn
|
||||||
|
(setf (inspections monkey) (1+ (inspections monkey)))
|
||||||
|
(setq level (funcall (op monkey) item))
|
||||||
|
(setq level (floor level div))
|
||||||
|
(setf (items monkey) (cons level (cdr (items monkey))))
|
||||||
|
(if (funcall (test monkey) level)
|
||||||
|
(throw-item monkeys (first (actions monkey)) (second (actions monkey)))
|
||||||
|
(throw-item monkeys (third (actions monkey)) (fourth (actions monkey)))))))
|
||||||
|
monkeys))
|
||||||
|
|
||||||
|
(defun solution (input div rounds)
|
||||||
|
"Run ROUNDS number of rounds on INPUT and use divisor DIV."
|
||||||
|
(let ((monkeys (parse-input input)))
|
||||||
|
(loop :for round :upto (1- rounds) :do
|
||||||
|
(run-round monkeys div))
|
||||||
|
(reduce '* (subseq (sort (loop :for monkey :in monkeys :collect (inspections monkey)) '>) 0 2))))
|
||||||
|
|
||||||
|
(solution "./input" 3 20)
|
||||||
|
(solution "./input" 1 10000)
|
||||||
55
day11/input
Normal file
55
day11/input
Normal file
@ -0,0 +1,55 @@
|
|||||||
|
Monkey 0:
|
||||||
|
Starting items: 91, 58, 52, 69, 95, 54
|
||||||
|
Operation: new = old * 13
|
||||||
|
Test: divisible by 7
|
||||||
|
If true: throw to monkey 1
|
||||||
|
If false: throw to monkey 5
|
||||||
|
|
||||||
|
Monkey 1:
|
||||||
|
Starting items: 80, 80, 97, 84
|
||||||
|
Operation: new = old * old
|
||||||
|
Test: divisible by 3
|
||||||
|
If true: throw to monkey 3
|
||||||
|
If false: throw to monkey 5
|
||||||
|
|
||||||
|
Monkey 2:
|
||||||
|
Starting items: 86, 92, 71
|
||||||
|
Operation: new = old + 7
|
||||||
|
Test: divisible by 2
|
||||||
|
If true: throw to monkey 0
|
||||||
|
If false: throw to monkey 4
|
||||||
|
|
||||||
|
Monkey 3:
|
||||||
|
Starting items: 96, 90, 99, 76, 79, 85, 98, 61
|
||||||
|
Operation: new = old + 4
|
||||||
|
Test: divisible by 11
|
||||||
|
If true: throw to monkey 7
|
||||||
|
If false: throw to monkey 6
|
||||||
|
|
||||||
|
Monkey 4:
|
||||||
|
Starting items: 60, 83, 68, 64, 73
|
||||||
|
Operation: new = old * 19
|
||||||
|
Test: divisible by 17
|
||||||
|
If true: throw to monkey 1
|
||||||
|
If false: throw to monkey 0
|
||||||
|
|
||||||
|
Monkey 5:
|
||||||
|
Starting items: 96, 52, 52, 94, 76, 51, 57
|
||||||
|
Operation: new = old + 3
|
||||||
|
Test: divisible by 5
|
||||||
|
If true: throw to monkey 7
|
||||||
|
If false: throw to monkey 3
|
||||||
|
|
||||||
|
Monkey 6:
|
||||||
|
Starting items: 75
|
||||||
|
Operation: new = old + 5
|
||||||
|
Test: divisible by 13
|
||||||
|
If true: throw to monkey 4
|
||||||
|
If false: throw to monkey 2
|
||||||
|
|
||||||
|
Monkey 7:
|
||||||
|
Starting items: 83, 75
|
||||||
|
Operation: new = old + 1
|
||||||
|
Test: divisible by 19
|
||||||
|
If true: throw to monkey 2
|
||||||
|
If false: throw to monkey 6
|
||||||
27
day11/input-test
Normal file
27
day11/input-test
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
Monkey 0:
|
||||||
|
Starting items: 79, 98
|
||||||
|
Operation: new = old * 19
|
||||||
|
Test: divisible by 23
|
||||||
|
If true: throw to monkey 2
|
||||||
|
If false: throw to monkey 3
|
||||||
|
|
||||||
|
Monkey 1:
|
||||||
|
Starting items: 54, 65, 75, 74
|
||||||
|
Operation: new = old + 6
|
||||||
|
Test: divisible by 19
|
||||||
|
If true: throw to monkey 2
|
||||||
|
If false: throw to monkey 0
|
||||||
|
|
||||||
|
Monkey 2:
|
||||||
|
Starting items: 79, 60, 97
|
||||||
|
Operation: new = old * old
|
||||||
|
Test: divisible by 13
|
||||||
|
If true: throw to monkey 1
|
||||||
|
If false: throw to monkey 3
|
||||||
|
|
||||||
|
Monkey 3:
|
||||||
|
Starting items: 74
|
||||||
|
Operation: new = old + 3
|
||||||
|
Test: divisible by 17
|
||||||
|
If true: throw to monkey 0
|
||||||
|
If false: throw to monkey 1
|
||||||
Loading…
x
Reference in New Issue
Block a user