unofficial mirror of help-gnu-emacs@gnu.org
 help / color / mirror / Atom feed
* hooks and let-bound variables
@ 2015-06-23 19:15 Alan Schmitt
  2015-06-23 21:44 ` Drew Adams
  0 siblings, 1 reply; 7+ messages in thread
From: Alan Schmitt @ 2015-06-23 19:15 UTC (permalink / raw)
  To: help-gnu-emacs

[-- Attachment #1: Type: text/plain, Size: 1268 bytes --]

Hello,

I’m trying to get eshell-autojump to work
(http://www.emacswiki.org/emacs/EshellAutojump) but I’m getting errors
about an undefined variable (curdir). This variable is bound by a let
before a hook is called:

#+begin_src emacs-lisp
      (let ((curdir (eshell/pwd)))
	(unless (equal curdir dired-directory)
	  (eshell-add-to-dir-ring curdir))
	(let ((result (cd dired-directory)))
	  (and eshell-cd-shows-directory
	       (eshell-printn result)))
	(run-hooks 'eshell-directory-change-hook)
        ...
#+end_src

and here is the hook that is called:

#+begin_src emacs-lisp
(defun eshell-autojump-record ()
  "Record the current directory.
`curdir' is set by `eshell/cd'."
  (unless eshell-autojump-map
    (eshell-autojump-load))
  (if (gethash curdir eshell-autojump-map)
      (puthash curdir (1+ (gethash curdir eshell-autojump-map)) eshell-autojump-map)
    (puthash curdir 1 eshell-autojump-map)))
#+end_src

I tried to edebug this, and curdir is set before the hook is called, but
it is not set in the called function. Is there a reason why it is not
set?

I'm using emacs 24.5.1.

Thanks,

Alan

-- 
OpenPGP Key ID : 040D0A3B4ED2E5C7
Weekly CO₂ average (2015-05-30, Mauna Loa Observatory): 403.41 ppm

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 472 bytes --]

^ permalink raw reply	[flat|nested] 7+ messages in thread

* RE: hooks and let-bound variables
  2015-06-23 19:15 hooks and let-bound variables Alan Schmitt
@ 2015-06-23 21:44 ` Drew Adams
  2015-06-24  9:13   ` Alan Schmitt
  0 siblings, 1 reply; 7+ messages in thread
From: Drew Adams @ 2015-06-23 21:44 UTC (permalink / raw)
  To: Alan Schmitt, help-gnu-emacs

> I’m trying to get eshell-autojump to work but I’m getting
> errors about an undefined variable (curdir). This variable is bound by a
> let before a hook is called:

Yes, but occurrences of that variable in the function called by the hook are not within the lexical scope of that let.

What happens if you add (defvar curdir), to let Emacs know that the variable is to be dynamically scoped?



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: hooks and let-bound variables
  2015-06-23 21:44 ` Drew Adams
@ 2015-06-24  9:13   ` Alan Schmitt
  2015-06-24 13:22     ` Drew Adams
  0 siblings, 1 reply; 7+ messages in thread
From: Alan Schmitt @ 2015-06-24  9:13 UTC (permalink / raw)
  To: help-gnu-emacs

[-- Attachment #1: Type: text/plain, Size: 1003 bytes --]

Hi Drew,

On 2015-06-23 23:44, Drew Adams <drew.adams@oracle.com> writes:

>> I’m trying to get eshell-autojump to work but I’m getting
>> errors about an undefined variable (curdir). This variable is bound by a
>> let before a hook is called:
>
> Yes, but occurrences of that variable in the function called by the hook are
> not within the lexical scope of that let.

It makes sense. And I now see the big "lexical-binding:t" at the top of
the file … I guess this was recently changed and is the reason it no
longer works.

> What happens if you add (defvar curdir), to let Emacs know that the variable
> is to be dynamically scoped?

It does not seem to work. Here is what I’m trying:

M-: (defvar curdir)

then use autojump, but it tells me the value of curdir is still void.
I guess I need to change the code of eshell for this to work …

Alan

-- 
OpenPGP Key ID : 040D0A3B4ED2E5C7
Athmospheric CO₂ average (2015-05-30, Mauna Loa Observatory): 403.41 ppm

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 472 bytes --]

^ permalink raw reply	[flat|nested] 7+ messages in thread

* RE: hooks and let-bound variables
  2015-06-24  9:13   ` Alan Schmitt
@ 2015-06-24 13:22     ` Drew Adams
  2015-06-24 13:35       ` Alan Schmitt
  0 siblings, 1 reply; 7+ messages in thread
From: Drew Adams @ 2015-06-24 13:22 UTC (permalink / raw)
  To: Alan Schmitt, help-gnu-emacs

> It makes sense. And I now see the big "lexical-binding:t" at the top
> of the file … I guess this was recently changed and is the reason it no
> longer works.
> 
> > What happens if you add (defvar curdir), to let Emacs know that
> > the variable is to be dynamically scoped?
> 
> It does not seem to work. Here is what I’m trying:
> M-: (defvar curdir)

Try putting that in the file that has the lexical-binding
declaration. Or evaluating that before that file gets compiled or
loaded.

> then use autojump, but it tells me the value of curdir is still
> void. I guess I need to change the code of eshell for this to work …

Maybe someone else will have a better suggestion.  But I think that's
the problem anyway: `curdir' is being handled as a lexical variable
when the code that invokes the hook function is run.



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: hooks and let-bound variables
  2015-06-24 13:22     ` Drew Adams
@ 2015-06-24 13:35       ` Alan Schmitt
  2015-06-24 14:44         ` Drew Adams
  0 siblings, 1 reply; 7+ messages in thread
From: Alan Schmitt @ 2015-06-24 13:35 UTC (permalink / raw)
  To: help-gnu-emacs

[-- Attachment #1: Type: text/plain, Size: 986 bytes --]

On 2015-06-24 15:22, Drew Adams <drew.adams@oracle.com> writes:

>> It does not seem to work. Here is what I’m trying:
>> M-: (defvar curdir)
>
> Try putting that in the file that has the lexical-binding
> declaration. Or evaluating that before that file gets compiled or
> loaded.
>
>> then use autojump, but it tells me the value of curdir is still
>> void. I guess I need to change the code of eshell for this to work …
>
> Maybe someone else will have a better suggestion.  But I think that's
> the problem anyway: `curdir' is being handled as a lexical variable
> when the code that invokes the hook function is run.

Thank you for the suggestions. The eshell-autojump author fixed it and
it’s now working correctly. (I find very funny that I only use languages
with lexical binding, but can still be bitten by it in emacs-lisp.)

Alan

-- 
OpenPGP Key ID : 040D0A3B4ED2E5C7
Athmospheric CO₂ average (2015-05-30, Mauna Loa Observatory): 403.41 ppm

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 472 bytes --]

^ permalink raw reply	[flat|nested] 7+ messages in thread

* RE: hooks and let-bound variables
  2015-06-24 13:35       ` Alan Schmitt
@ 2015-06-24 14:44         ` Drew Adams
  2015-06-24 15:48           ` tomas
  0 siblings, 1 reply; 7+ messages in thread
From: Drew Adams @ 2015-06-24 14:44 UTC (permalink / raw)
  To: Alan Schmitt, help-gnu-emacs

> I find very funny that I only use languages with lexical binding,
> but can still be bitten by it in emacs-lisp.

;-)

Yup.  If you have only lexical binding then you cannot be bitten
by it (or by dynamic binding).

Emacs makes (good) use of dynamic binding, for exactly the kind
of thing you were doing: let-binding around some code whose behavior
you want to change by way of the binding.

In most languages you do not ever want the behavior of existing code
to change at runtime by just changing the value of a global variable
(i.e, from outside that code).  With Common Lisp and Emacs Lisp you
do sometimes want that.

http://www.gnu.org/software/emacs/emacs-paper.html#SEC17



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: hooks and let-bound variables
  2015-06-24 14:44         ` Drew Adams
@ 2015-06-24 15:48           ` tomas
  0 siblings, 0 replies; 7+ messages in thread
From: tomas @ 2015-06-24 15:48 UTC (permalink / raw)
  To: Drew Adams; +Cc: Alan Schmitt, help-gnu-emacs

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

On Wed, Jun 24, 2015 at 07:44:33AM -0700, Drew Adams wrote:
> > I find very funny that I only use languages with lexical binding,
> > but can still be bitten by it in emacs-lisp.
> 
> ;-)
> 
> Yup.  If you have only lexical binding then you cannot be bitten
> by it (or by dynamic binding).
> 
> Emacs makes (good) use of dynamic binding, for exactly the kind
> of thing you were doing: let-binding around some code whose behavior
> you want to change by way of the binding.
> 
> In most languages you do not ever want the behavior of existing code
> to change at runtime by just changing the value of a global variable
> (i.e, from outside that code).  With Common Lisp and Emacs Lisp you
> do sometimes want that.

Perl is another language with dual binding: it started out with "local"
(dynamically bound, in good ol' shell tradition) and then grew (I
think it's an appropriate term for Perl ;-) "my" for lexical binding,
with all the niceness of closures, etc.

Then, loads of well-meant advice ("never use 'local', you want 'my'").
I think a language having both is a very nice trait.

- -- t
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.12 (GNU/Linux)

iEYEARECAAYFAlWK0TcACgkQBcgs9XrR2kYXwwCfV6wP6C6nUaMgSKH0D7RFjEsH
tUEAnAxjn/I0YgjWz36tjLsBCh4QgLWY
=0mcS
-----END PGP SIGNATURE-----



^ permalink raw reply	[flat|nested] 7+ messages in thread

end of thread, other threads:[~2015-06-24 15:48 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2015-06-23 19:15 hooks and let-bound variables Alan Schmitt
2015-06-23 21:44 ` Drew Adams
2015-06-24  9:13   ` Alan Schmitt
2015-06-24 13:22     ` Drew Adams
2015-06-24 13:35       ` Alan Schmitt
2015-06-24 14:44         ` Drew Adams
2015-06-24 15:48           ` tomas

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).