help-gnu-emacs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: TIL: buffer-local variables are used over let-bound variables when u


From: Eli Zaretskii
Subject: Re: TIL: buffer-local variables are used over let-bound variables when using with-current-buffer in let
Date: Sun, 22 Oct 2023 08:59:56 +0300

> From: Rodrigo Morales <moralesrodrigo1100@gmail.com>
> Date: Sun, 22 Oct 2023 05:45:11 +0000
> 
> TIL: buffer-local variables are used over let-bound variables when using
> with-current-buffer in let
> 
> Let's suppose we have a directory =/tmp/foo=
> 
> #+BEGIN_SRC elisp
> (dired-create-directory "/tmp/foo")
> #+END_SRC
> 
> Now, let's suppose we create a buffer while =/tmp/foo= is
> =default-directory=.
> 
> #+BEGIN_SRC elisp
> (let ((default-directory "/tmp/foo"))
>  (get-buffer-create "*foo*"))
> #+END_SRC
> 
> Now, let's suppose we have another directory =/tmp/bar=.
> 
> #+BEGIN_SRC elisp
> (dired-create-directory "/tmp/bar")
> #+END_SRC
> 
> The result of evaluation of the following sexp is =/tmp/foo=.
> #+HEADER: :results value
> #+BEGIN_SRC elisp
> (let ((default-directory "/tmp/bar"))
>  (with-current-buffer (get-buffer "*foo*")
>   default-directory))
> #+END_SRC
> 
> #+RESULTS:
> #+begin_example
> /tmp/foo
> #+end_example
> 
> Some users would expect for the result to be  =/tmp/bar= because
> =default-directory= has been modified in =let=. However that's not the case
> because when we change to buffer =*foo*=, the variable =default-directory==
> has another value.

What you describe is precisely the expected behavior: 'let' rebinds
the binding that's currently in effect.  The ELisp manual says:

     *Warning:* When a variable has buffer-local bindings in one or more
  buffers, ‘let’ rebinds the binding that’s currently in effect.  For
  instance, if the current buffer has a buffer-local value, ‘let’
  temporarily rebinds that.  If no buffer-local bindings are in effect,
  ‘let’ rebinds the default value.  If inside the ‘let’ you then change to
  a different current buffer in which a different binding is in effect,
  you won’t see the ‘let’ binding any more.  And if you exit the ‘let’
  while still in the other buffer, you won’t see the unbinding occur
  (though it will occur properly).



reply via email to

[Prev in Thread] Current Thread [Next in Thread]