I don’t have anything else interesting to say today so let’s take a look at Mike Zamansky’s post on the Advent of Code 2017 Day 1 problem. Zamansky has a nice discussion of solving this with Python and the steps you might go through to arrive at a clean solution. You should read his post to see the problem statement. When I saw the problem, the first thing I thought of was using one of the Lisp mapping functions to step through the digits. Here’s my solution in Emacs Lisp:
(defun cksum (captcha) (interactive) ;for interactive testing (let ((checksum 0) (digits (mapcar (lambda (a) (- a 48)) captcha))) (cl-mapc (lambda (a b) (when (= a b) (cl-incf checksum a))) digits (-rotate -1 digits)) checksum)) (cksum "234445662") → 16
The first thing you notice is that it’s really a Common Lisp solution because it makes use of
cl-incf. You could do without the
cl-incf but the Elisp
mapc operates on only one sequence. You’ll also need Magnar Sveen’s Dash library but if you have any packages at all installed, it’s probably already been pulled in; otherwise you’ll need a
We need two sequences because the logic depends on
seq1[i+1] = seq2[i]. Notice that this handles the “wraparound case” as well. The second half of the problem is the same except the two lists should be the first and second half of the digits. One nice thing about the Emacs mapping functions is that they operate on any sequence, not just lists. That’s convenient in this problem.