For a discussion, see DynamicBindingVsLexicalBinding.
Emacs 24 has optional lexical binding, which can be enabled on a per-buffer basis.
To use it, set the buffer-local variable
‘lexical-binding’ to a non-
For closures on previous versions of Emacs, see FakeClosures.
(setq lexical-binding t) (setq test (let ((foo "bar")) (lambda () foo))) => (closure ((foo . "bar") t) nil foo) (funcall test) => "bar" ; without lexical binding, it would have failed due to an unbound variable (let ((foo "something-else")) (funcall test)) => "bar" ; without lexical binding, it would have returned "something-else"
Prior to Emacs 24.3, the
defun special form didn’t work properly in lexically bound contexts (i.e. when the buffer-local variable
lexical-binding in not
nil). For example:
(let ((counter 0)) (defun counting () (setq counter (1+ counter))))
would not work as expected because the symbol
counter in the function’s body would be dynamically bound instead of binding to the variable defined in the
The byte compiler did give a warning if you used
defun in this way.
This issue was resolved in Emacs 24.3, where the
defun special form was replaced by a macro that doesn’t have this issue.
In versions prior to 24.3, the following macro can be used as a work-around:
(defmacro defun** (name arglist &rest body) "Define NAME as a function in a lexically bound context. Like normal `defun', except that it works correctly in lexically bound contexts in versions of Emacs 24 prior to 24.3. \(fn NAME ARGLIST [DOCSTRING] BODY...)" (when (fboundp `,name) (message "Redefining function/macro: %s" `,name)) `(eval-and-compile (fset (quote ,name) (lambda (,@arglist) ,@body))))
If you define
counting as follows:
(let ((counter 0)) (defun** counting () (setq counter (1+ counter))))
it will work as expected and update the lexically bound variable
counter every time it is invoked, while returning the new value.
NOTE: The macro always makes a globally visible function even if you try to use it in a lexical closure. For instance, if you do the following:
(let ((something 10)) (defun** something () ......... .........))
you get a lexical closure with a variable binding for the symbol
something, but the function being defined will still be stored in the function cell of the symbol
something, which is global. In short, remember that elisp is a lisp-2, and
let binds variables only.
If you want lexically bound functions, you can use
cl-lables from the cl package.
Alternatively, you can assign lambdas to variables and then use them with
funcall, for example:
(let ((foo (lambda () "I am foo."))) (defun bar () (funcall foo))) (bar) => "I am foo."
However, like with
cl-flet, this doesn’t allow the functions to recurse.
For recursion you need more machinery. The
make-rec macro (below) takes a name, and a function (which may use that name) and returns an anonymous recursive function. (Note: the use of
funcall is still required)
(defmacro make-rec (name fun) `((lambda (x) (funcall x x)) (lambda (y) (funcall (lambda (,name) ,fun) (lambda (&rest args) (apply (funcall y y) args)))))) (let ((fac (make-rec f (lambda (n) (if (= n 0) 1 (* n (funcall f (1- n)))))))) (defun bar (n) (funcall fac n))) (bar 5) => 120
Note: I have named the macro
defun** so that it doesn’t clash with the macro
defun* in the cl package, however it doesn’t depend on that package. — Bernard Hurley
To enable lexical binding in your elisp library, put a line like this at the top of the file:
;; -*- lexical-binding: t -*-
This will enable lexical-binding for the code in the file, but note that global variables declared with
defconst will be dynamically bound due to the global binding being marked as “special” by those forms.
Note: as of Emacs 24.4, any closures created before marking the variable as “special” are unaffected by this effect. It’s not clear whether this is intentional. (I could reproduce this in SBCL, but not CLISP. Maybe it’s supposed to have undefined behavior.)
Note: as of Emacs 24.4, the undocumented
internal-make-var-non-special function does not work as expected, and the only known way to revert a special variable status is restarting Emacs.
makunbound doesn’t help, either.
One problem with using lexical binding is debugging.
‘eval’ in especially in edebbug is unusable because the
‘print’ed version of the closures would take half a screen. Is there any way to tell emacs to reduce the printout a closure (e.g. #<closure>)? --LinhDang