The following emacs lisp file is about seeing what happens when Alice uses a lexically bound local variable foo
in her init file and Bob defines foo
as a global special variable with defvar
in his init file and Alice borrows part of Bob's init file code into her own init file not knowing that foo
is going to turn special.
;; -*- lexical-binding: t; -*-
;; Alice init file
;; Alice defining alice-multiplier
(defun alice-multiplier-1 (foo)
(lambda (n) (* n foo)))
(defun alice-multiplier-2 (num)
(let ((foo num))
(lambda (n) (* n foo))))
;; Alice using alice-multiplier
(print
(list
:R1 (mapcar (alice-multiplier-1 10) (list 1 2 3))
:R2 (mapcar (alice-multiplier-2 10) (list 1 2 3))))
;; from Bob's code
;; ...
(defvar foo 1000)
;; ...
;; Alice using alice-multiplier
(print
(list
:R3 (mapcar (alice-multiplier-1 10) (list 1 2 3))
:R4 (mapcar (alice-multiplier-2 10) (list 1 2 3))))
Output:
(:R1 (10 20 30) :R2 (10 20 30))
(:R3 (10 20 30) :R4 (1000 2000 3000))
Results R1 and R2 are just as what I expect. Result R4 is consistent with defvar documentation, although it may surprise Alice unless she reads Bob's code.
I find R3 surprising. Why is R3 like that?
Speaking of R4, what can Alice do to protect her
foo
from turning special by others? For example,foo
may be a lexical local variable she uses in her init file or one of her emacs package, and(defvar foo "something")
may be in some of the packages she happens to use, orfoo
could be one of the new special variable names introduced by a future version of Emacs. Is there something Alice can put in her file that says to Emacs "In this file, foo should be always lexical, even if some code from outside happens to use a special variable of the same name"?