I have a simple alist in elisp like this:

(defvar *oneliners*
  '((js . "//")
    (python . "#")

I am a bit surprised that searching for the python key gives me nil. I am calling it from within the function:

(defun one (lang)
  (cdr (assoc lang *oneliners*)))

(one 'js) ;; -> "//"


(one 'python) ;; -> nil

What am i missing about elisp's alists?

  • 2
    Note that the initial value is used only if the current value is void. That is, if you change the value in the defvar, then evaluate the defvar again, the value is not updated. You can use setq to change the value (or use defconst instead of defvar). – JeanPierre Aug 26 '19 at 11:49
  • If this turns out to be your problem, I'll post an answer detailing that. – JeanPierre Aug 26 '19 at 11:51
  • Yes that was the problem, what is the elisp counterpart of CL defparameter? – user12021 Aug 26 '19 at 11:54
  • I dont know CL so I can't say. – JeanPierre Aug 26 '19 at 12:05
  • 2
    @amirt See emacs.stackexchange.com/questions/35294/… – Tobias Aug 26 '19 at 12:35

One thing that may be unexpected with defvar is that (from its docstring):

The optional argument INITVALUE is evaluated, and used to set SYMBOL, only if SYMBOL’s value is void.

That is, if you change the initvalue in the defvar and evaluate it again (eg with eval-last-sexp, the new initvalue is not taken into account. However, you can use the command eval-defun (bound to C-M-x in elisp-mode)

If the current defun is actually a call to ‘defvar’ or ‘defcustom’, evaluating it this way resets the variable using its initial value expression (using the defcustom’s :set function if there is one), even if the variable already has some other value.

Note that defconst does not have this behavior (from its docstring):

The ‘defconst’ form always sets the value of SYMBOL to the result of evalling INITVALUE.

| improve this answer | |

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy