Can someone explain to me why the code below throws an error (void-function fn)?

(let ((lexical-binding t)
      (fn (lambda (y) (+ y 4)))
      (x 4))
  (pcase x
    (10 (- x 2))
    (4 (fn x))))

and is there a way to fix it without defun'ing a function?

  • 4
    let binds variables, not functions. So fn is a variable whose value is a function. You need to call it as (funcall fn x).
    – Basil
    Commented Jun 22, 2020 at 9:30
  • Ah of course. Thanks!
    – Tohiko
    Commented Jun 22, 2020 at 9:36
  • @Basil: Please consider posting that answer as an answer. Comments can be deleted at any time. But maybe check also to see whether the question is a duplicate. Thx.
    – Drew
    Commented Jun 22, 2020 at 14:45
  • I have a feeling this question is a dup. I suggest searching for void-function... and maybe tag [debugging].
    – Drew
    Commented Jun 22, 2020 at 14:48
  • @Drew I'm also pretty sure it's a duplicate but I can't find the original.
    – Basil
    Commented Jun 22, 2020 at 15:05

1 Answer 1


Emacs is a “Lisp-2”: functions and values have separate namespaces. A function definition (defun foo …) and a function call (foo …) use the function slot of the symbol foo. A variable assignment (setq foo …), a variable binding (let ((foo …)) …), and a variable reference x use the value slot of the symbol foo.

To call a function which is stored in the value slot of a symbol, use funcall.

(funcall fn x)

More generally, but infrequently, the argument to funcall can be any Lisp expression. funcall is an ordinary function.

Lisp functions take a list of arguments. Sometimes, in addition to calling a variable function, you need to call the function with a variable list of arguments. In this case, use apply instead of funcall. The last argument to apply is used as a list of remaining arguments.

In this particular case, where the code of the function is fully known, you can also use cl-flet from the CL library that is distributed with Emacs. This doesn't let you easily pass the function around, which may or may not be an issue in your real program.

(require 'cl-lib)
(let ((lexical-binding t)
      (x 4))
  (cl-flet ((fn (y) (+ y 4)))
    (pcase x
      (10 (- x 2))
      (4 (fn x)))))

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.