From: Osei
Subject: Lexical scope question
Date: 
Message-ID: <1184275659.975402.291590@n2g2000hse.googlegroups.com>
Im afraid this is another newbie scope question.  Given the
following...

(defparameter myparam "global")

(defun test-inner ()
      (format t "myparam is: ~A~%" myparam))

(defun test-outer1 ()
      (let ((myparam "lexical"))
          (test-inner)))

(defun test-outer2 ()
      (let ((myparam "lexical"))
         (lambda ()
             (test-inner))))

> (test-outer1)
prints=> myparam is: lexical

;; yeah the call to test-inner is closed around the new binding for
myparam

> (funcall (test-outer2))
prints=> myparam is: global

;; ??  what happened to the lexical binding of myparam

I hope my confusion is clear.  I expect the lexical binding to be in
both cases.  I even tried

(defun test-outer3 ()
           (let ((myparam "lexical"))
             (flet ((fun ()
                      (test-inner)))
               #'fun)))

and I still lose the lexical binding.

Any help is appreciated.

Osei

From: Jock Cooper
Subject: Re: Lexical scope question
Date: 
Message-ID: <87fy3tfero.fsf@mail.com>
Osei <·········@gmail.com> writes:

> Im afraid this is another newbie scope question.  Given the
> following...
> 
> (defparameter myparam "global")
> 
> (defun test-inner ()
>       (format t "myparam is: ~A~%" myparam))
> 
> (defun test-outer1 ()
>       (let ((myparam "lexical"))
>           (test-inner)))
> 
> (defun test-outer2 ()
>       (let ((myparam "lexical"))
>          (lambda ()
>              (test-inner))))
> 
> > (test-outer1)
> prints=> myparam is: lexical
> 
> ;; yeah the call to test-inner is closed around the new binding for
> myparam
> 
> > (funcall (test-outer2))
> prints=> myparam is: global
> 
> ;; ??  what happened to the lexical binding of myparam
> 
> I hope my confusion is clear.  I expect the lexical binding to be in
> both cases.  I even tried
> 
> (defun test-outer3 ()
>            (let ((myparam "lexical"))
>              (flet ((fun ()
>                       (test-inner)))
>                #'fun)))
> 
> and I still lose the lexical binding.
> 
> Any help is appreciated.
> 
> Osei

The lambda does not run in the lexical scope; by the time it runs
that lexical scope is gone.  myparam is a special var so the lambda 
looks for its dynamic binding.

USER> (let ((myparam "lexical")) (funcall (test-outer2)))
myparam is lexical

Also note:

(defun test-outer4 ()
      (let* ((myparam "lexical")      ; special
             (saved-myparam myparam)) ; lexical not special
        (lambda ()
           (test-inner)
           ; saved-myparam is closure var
           (let ((myparam saved-myparam)) ; create dynamic bind
             (test-inner)))))
TEST-OUTER4
USER>  (funcall (test-outer4))
              
myparam is global
myparam is lexical
From: Rainer Joswig
Subject: Re: Lexical scope question
Date: 
Message-ID: <joswig-3720AF.00105513072007@news-europe.giganews.com>
In article <··············@mail.com>, Jock Cooper <·····@mail.com> 
wrote:

> Osei <·········@gmail.com> writes:
> 
> > Im afraid this is another newbie scope question.  Given the
> > following...
> > 
> > (defparameter myparam "global")
> > 
> > (defun test-inner ()
> >       (format t "myparam is: ~A~%" myparam))
> > 
> > (defun test-outer1 ()
> >       (let ((myparam "lexical"))
> >           (test-inner)))
> > 
> > (defun test-outer2 ()
> >       (let ((myparam "lexical"))
> >          (lambda ()
> >              (test-inner))))
> > 
> > > (test-outer1)
> > prints=> myparam is: lexical
> > 
> > ;; yeah the call to test-inner is closed around the new binding for
> > myparam
> > 
> > > (funcall (test-outer2))
> > prints=> myparam is: global
> > 
> > ;; ??  what happened to the lexical binding of myparam
> > 
> > I hope my confusion is clear.  I expect the lexical binding to be in
> > both cases.  I even tried
> > 
> > (defun test-outer3 ()
> >            (let ((myparam "lexical"))
> >              (flet ((fun ()
> >                       (test-inner)))
> >                #'fun)))
> > 
> > and I still lose the lexical binding.
> > 
> > Any help is appreciated.
> > 
> > Osei
> 
> The lambda does not run in the lexical scope; by the time it runs
> that lexical scope is gone.  myparam is a special var so the lambda 
> looks for its dynamic binding.
> 
> USER> (let ((myparam "lexical")) (funcall (test-outer2)))
> myparam is lexical

Above LET creates a dynamic binding for a special variable MYPARAM.

> 
> Also note:
> 
> (defun test-outer4 ()
>       (let* ((myparam "lexical")      ; special
>              (saved-myparam myparam)) ; lexical not special
>         (lambda ()
>            (test-inner)
>            ; saved-myparam is closure var
>            (let ((myparam saved-myparam)) ; create dynamic bind
>              (test-inner)))))
> TEST-OUTER4
> USER>  (funcall (test-outer4))
>               
> myparam is global
> myparam is lexical

-- 
http://lispm.dyndns.org
From: Rainer Joswig
Subject: Re: Lexical scope question
Date: 
Message-ID: <joswig-899431.23575212072007@news-europe.giganews.com>
In article <························@n2g2000hse.googlegroups.com>,
 Osei <·········@gmail.com> wrote:

> Im afraid this is another newbie scope question.  Given the
> following...
> 
> (defparameter myparam "global")
> 
> (defun test-inner ()
>       (format t "myparam is: ~A~%" myparam))

MYPARAM refers to a special variable. It is
not a lexical variable.

> 
> (defun test-outer1 ()
>       (let ((myparam "lexical"))
>           (test-inner)))

This is not lexical. MYPARAM is globally declared to be special.
This effects also local uses of this variable in LET bindings.

> 
> (defun test-outer2 ()
>       (let ((myparam "lexical"))
>          (lambda ()
>              (test-inner))))

There is no lexical binding, since MYPARAM is globally
declared to be special. There is also no usage
if it, if it were lexical.

> 
> > (test-outer1)
> prints=> myparam is: lexical


But is not lexical binding. It is an example
for dynamic binding.
You have declared MYPARAM to be special, because you
used DEFPARAMETER. Now it will be special everywhere.
The example shows it clearly. It is 'dynamic' not lexical.

> 
> ;; yeah the call to test-inner is closed around the new binding for
> myparam
> 
> > (funcall (test-outer2))
> prints=> myparam is: global

That's simple. MYPARAM in TEST-INNER is a special variable.
At runtime there is no other binding active, only
the global value is available.


> 
> ;; ??  what happened to the lexical binding of myparam

Nothing, since there was no lexical binding. It was
dynamic.

> 
> I hope my confusion is clear.  I expect the lexical binding to be in
> both cases.  I even tried
> 
> (defun test-outer3 ()
>            (let ((myparam "lexical"))
>              (flet ((fun ()
>                       (test-inner)))
>                #'fun)))
> 
> and I still lose the lexical binding.

Same problem. MYPARAM is already globally declared to be special.
So it is a dynamic variable. There is also no usage
of it if it were lexical.

> 
> Any help is appreciated.

This is a classical example for dynamic binding:

(defparameter *myparam* "global")

(defun test-inner ()
   (format t "myparam is: ~A~%" *myparam*))

(defun test-outer1 ()
   (let ((*myparam* "dynamic"))
         (test-inner)))

> 
> Osei

-- 
http://lispm.dyndns.org
From: Osei
Subject: Re: Lexical scope question
Date: 
Message-ID: <1184279661.459366.310180@n60g2000hse.googlegroups.com>
On Jul 12, 5:57 pm, Rainer Joswig <······@lisp.de> wrote:
> In article <························@n2g2000hse.googlegroups.com>,
>
>  Osei <·········@gmail.com> wrote:
> > Im afraid this is another newbie scope question.  Given the
> > following...
>
> > (defparameter myparam "global")
>
> > (defun test-inner ()
> >       (format t "myparam is: ~A~%" myparam))
>
> MYPARAM refers to a special variable. It is
> not a lexical variable.
>
>
>
> > (defun test-outer1 ()
> >       (let ((myparam "lexical"))
> >           (test-inner)))
>
> This is not lexical. MYPARAM is globally declared to be special.
> This effects also local uses of this variable in LET bindings.
>
>
>
> > (defun test-outer2 ()
> >       (let ((myparam "lexical"))
> >          (lambda ()
> >              (test-inner))))
>
> There is no lexical binding, since MYPARAM is globally
> declared to be special. There is also no usage
> if it, if it were lexical.
>
>
>
> > > (test-outer1)
> > prints=> myparam is: lexical
>
> But is not lexical binding. It is an example
> for dynamic binding.
> You have declared MYPARAM to be special, because you
> used DEFPARAMETER. Now it will be special everywhere.
> The example shows it clearly. It is 'dynamic' not lexical.
>
>
>
> > ;; yeah the call to test-inner is closed around the new binding for
> > myparam
>
> > > (funcall (test-outer2))
> > prints=> myparam is: global
>
> That's simple. MYPARAM in TEST-INNER is a special variable.
> At runtime there is no other binding active, only
> the global value is available.
>
>
>
> > ;; ??  what happened to the lexical binding of myparam
>
> Nothing, since there was no lexical binding. It was
> dynamic.
>
>
>
> > I hope my confusion is clear.  I expect the lexical binding to be in
> > both cases.  I even tried
>
> > (defun test-outer3 ()
> >            (let ((myparam "lexical"))
> >              (flet ((fun ()
> >                       (test-inner)))
> >                #'fun)))
>
> > and I still lose the lexical binding.
>
> Same problem. MYPARAM is already globally declared to be special.
> So it is a dynamic variable. There is also no usage
> of it if it were lexical.
>
>
>
> > Any help is appreciated.
>
> This is a classical example for dynamic binding:
>
> (defparameter *myparam* "global")
>
> (defun test-inner ()
>    (format t "myparam is: ~A~%" *myparam*))
>
> (defun test-outer1 ()
>    (let ((*myparam* "dynamic"))
>          (test-inner)))
>
>

Wow.  I completely swapped the meanings dynamic and lexical.
I understand what you are saying though.  However before I ask
any more newbie questions I'm going to spend some time reading this.
http://www.flownet.com/ron/specials.pdf  as suggest somewhere else
in this group.

Hopefully things will be cleared up.

Thanks.

>
> > Osei
>
> --http://lispm.dyndns.org
From: Rainer Joswig
Subject: Re: Lexical scope question
Date: 
Message-ID: <joswig-52D9CC.00410913072007@news-europe.giganews.com>
In article <························@n60g2000hse.googlegroups.com>,
 Osei <·········@gmail.com> wrote:

...

> > > Any help is appreciated.
> >
> > This is a classical example for dynamic binding:
> >
> > (defparameter *myparam* "global")
> >
> > (defun test-inner ()
> >    (format t "myparam is: ~A~%" *myparam*))
> >
> > (defun test-outer1 ()
> >    (let ((*myparam* "dynamic"))
> >          (test-inner)))
> >
> >
> 
> Wow.  I completely swapped the meanings dynamic and lexical.
> I understand what you are saying though.  However before I ask
> any more newbie questions I'm going to spend some time reading this.
> http://www.flownet.com/ron/specials.pdf  as suggest somewhere else
> in this group.
> 
> Hopefully things will be cleared up.
> 
> Thanks.

Don't hesitate to ask. You wrote some code and
you described what you thought it should do.
That's how I (we?) like newbies to ask those questions. ;-)
Understanding the difference between dynamic and
lexical binding is quite important if you want to
understand programming in Common Lisp. Other important
concepts are evaluation, macros, recursion and so on...

> 
> >
> > > Osei
> >
> > --http://lispm.dyndns.org

-- 
http://lispm.dyndns.org
From: Osei
Subject: Re: Lexical scope question
Date: 
Message-ID: <1184285287.349136.57770@57g2000hsv.googlegroups.com>
>
> Don't hesitate to ask. You wrote some code and
> you described what you thought it should do.
> That's how I (we?) like newbies to ask those questions. ;-)
> Understanding the difference between dynamic and
> lexical binding is quite important if you want to
> understand programming in Common Lisp. Other important
> concepts are evaluation, macros, recursion and so on...
>

Thanks.  This isn't so scary after all :)

Since you insist... more questions (I finished and hopefully
understood that article)
Given...

(defun inner () (format t "~A~%" var))

(defun outer1 ()
  (let ((var "dynamic"))
     (declare (special var))   ; because of this DECLARE
     (inner)                                ; this will use dynamic
binding of var correctly
))

(outer1) prints "dynamic\n"

what i really want to do is to get the same output with the ff...

(defun outer2 ()
  (let ((var "dynamic"))
     (declare (special var))
     (lambda () (inner))
))

I want to do

(funcall (outer2))

and get the same output but  this is an error since the dynamic
binding of var is lost outside of OUTER2.

Is there any way to call the lambda function outside outer2 and still
get the binding it had inside or do I have to define INNER using FLET
inside OUTER2.

I hope this is clear.

Osei
From: Rainer Joswig
Subject: Re: Lexical scope question
Date: 
Message-ID: <joswig-CC7E27.02402713072007@news-europe.giganews.com>
In article <·······················@57g2000hsv.googlegroups.com>,
 Osei <·········@gmail.com> wrote:

> >
> > Don't hesitate to ask. You wrote some code and
> > you described what you thought it should do.
> > That's how I (we?) like newbies to ask those questions. ;-)
> > Understanding the difference between dynamic and
> > lexical binding is quite important if you want to
> > understand programming in Common Lisp. Other important
> > concepts are evaluation, macros, recursion and so on...
> >
> 
> Thanks.  This isn't so scary after all :)
> 
> Since you insist... more questions (I finished and hopefully
> understood that article)
> Given...
> 
> (defun inner () (format t "~A~%" var))
> 
> (defun outer1 ()
>   (let ((var "dynamic"))
>      (declare (special var))   ; because of this DECLARE
>      (inner)                                ; this will use dynamic
> binding of var correctly
> ))
> 
> (outer1) prints "dynamic\n"
> 
> what i really want to do is to get the same output with the ff...
> 
> (defun outer2 ()
>   (let ((var "dynamic"))
>      (declare (special var))
>      (lambda () (inner))
> ))
> 
> I want to do
> 
> (funcall (outer2))
> 
> and get the same output but  this is an error since the dynamic
> binding of var is lost outside of OUTER2.
> 
> Is there any way to call the lambda function outside outer2 and still
> get the binding it had inside or do I have to define INNER using FLET
> inside OUTER2.
> 
> I hope this is clear.
> 
> Osei

At runtime, the LAMBDA function will be called and there is no binding
for VAR. So you would need to introduce one. You can move the LET
into the LAMBDA function:


(defun outer2 ()
  (lambda ()
    (let ((var "dynamic"))
      (declare (special var))
      (inner))))
From: Kent M Pitman
Subject: Re: Lexical scope question
Date: 
Message-ID: <uir8pun1g.fsf@nhplace.com>
Rainer Joswig <······@lispmachine.de> writes:

> In article <·······················@57g2000hsv.googlegroups.com>,
>  Osei <·········@gmail.com> wrote:
> 
> > >
> > > Don't hesitate to ask. You wrote some code and
> > > you described what you thought it should do.
> > > That's how I (we?) like newbies to ask those questions. ;-)
> > > Understanding the difference between dynamic and
> > > lexical binding is quite important if you want to
> > > understand programming in Common Lisp. Other important
> > > concepts are evaluation, macros, recursion and so on...
> > >
> > 
> > Thanks.  This isn't so scary after all :)
> > 
> > Since you insist... more questions (I finished and hopefully
> > understood that article)
> > Given...
> > 
> > (defun inner () (format t "~A~%" var))
> > 
> > (defun outer1 ()
> >   (let ((var "dynamic"))
> >      (declare (special var))   ; because of this DECLARE
> >      (inner)                                ; this will use dynamic
> > binding of var correctly
> > ))
> > 
> > (outer1) prints "dynamic\n"
> > 
> > what i really want to do is to get the same output with the ff...
> > 
> > (defun outer2 ()
> >   (let ((var "dynamic"))
> >      (declare (special var))
> >      (lambda () (inner))
> > ))
> > 
> > I want to do
> > 
> > (funcall (outer2))
> > 
> > and get the same output but  this is an error since the dynamic
> > binding of var is lost outside of OUTER2.
> > 
> > Is there any way to call the lambda function 

Terminology:  It's not a lambda function.  It's an anonymous function.

There are lambda expressions, which are (lambda (x) x).  
Those are forms, not values.  As values, they are lists, not functions.

There are lambda combinations, which CL also calls lambda forms,
which are ((lambda (x) x) 3).   These are also forms, not values.
As values, they are again just lists.

A function is what results from these.  It has no more use of LAMBDA
and more than (A B C) has parens in it after it's been through the reader
or any more than (* 3 4) is a "times" number after the multiplication is done
and 12 is returned.  It's not a times 12.  It's just a twelve.

(lambda (x) x) returns a function, not a lambda function.
Before it is a lambda function, it is a list whose car is lambda,
[possible to view as a form whose operator is the name of the LAMBDA
macro].

> > outside outer2 and still get the binding it had inside 

You're asking to remember a value that had been dynamic by effectively
snapshotting it.  See last my example, OUTER4, below.

> > or do I have to define INNER using FLET
> > inside OUTER2.

No.

> > I hope this is clear.

It is if I've answered your question, and it's not if I haven't.
Heh.

> > Osei
> 
> At runtime, the LAMBDA function 

Anonymous function resulting from the lambda expression.

> will be called and there is no binding
> for VAR. So you would need to introduce one. You can move the LET
> into the LAMBDA function:
> 
> (defun outer2 ()
>   (lambda ()
>     (let ((var "dynamic"))
>       (declare (special var))
>       (inner))))

Which is, of course, the same as, and probably slower than:

 (defun outer3 ()
   (lambda ()
     (inner3 var)))

 (defun inner3 (&optional (var (symbol-value 'var)))
   (format t "~A~%" var))

I think the idiom Osei is looking for is:

 (defun outer4 ()
   (let ((var "dynamic"))
     (declare (special var))
     (inner4)))

 (defun inner4 ()
   (let ((var (symbol-value 'var))) ;capture a dynamic value as a static value
     #'(lambda () (write-line var))))

 (funcall (outer4))
 dynamic
 => "dynamic"


You could also write inner4 as having

 (let ((var (locally 
              (declare (special var))
              var)))
   ...)

if you didn't want to admit to yourself that (symbol-value 'var)
is the same as (locally (declare (special var)) var).
From: Kent M Pitman
Subject: Re: Lexical scope question
Date: 
Message-ID: <uejjdumvm.fsf@nhplace.com>
Kent M Pitman <······@nhplace.com> writes:

>    (let ((var (symbol-value 'var))) ;capture a dynamic value as a static value

Before anyone corrects me, I'll do it myself.  I should have said
lexical here, not static.  Static will probably confuse the C++ crowd
and isn't really the right term anyway.  And for that matter, I would
have been more clear writing

 ; Capture value of dynamic variable in a lexical variable.

I was just out of margin space and in a hurry.  Then I regretted it.
(It helps me understand how Fermat thought it acceptable to leave out
that pesky proof... sometimes these things just don't work out 
typographically.)
From: Matthias Buelow
Subject: Re: Lexical scope question
Date: 
Message-ID: <5fo2rpF3d5027U1@mid.dfncis.de>
Kent M Pitman wrote:

>    (let ((var (symbol-value 'var))) ;capture a dynamic value as a static value

isn't this the same as just (let ((var var)) ...) in this case?
From: Matthias Buelow
Subject: Re: Lexical scope question
Date: 
Message-ID: <5fo39nF3cfhh7U1@mid.dfncis.de>
I wrote:
> Kent M Pitman wrote:
> 
>>    (let ((var (symbol-value 'var))) ;capture a dynamic value as a static value
> 
> isn't this the same as just (let ((var var)) ...) in this case?

Actually, I'm somewhat puzzled as to why (symbol-value 'var) works
(which it apparently does, at least in clisp)... I mean, declaring the
lexical var special doesn't turn it into a global variable (i.e., a
symbol's value slot)? If anyone could enlighten me here?
From: Matthias Buelow
Subject: Re: Lexical scope question
Date: 
Message-ID: <5fo3m1F3d2ngiU1@mid.dfncis.de>
I wrote:

> Actually, I'm somewhat puzzled as to why (symbol-value 'var) works
> (which it apparently does, at least in clisp)... I mean, declaring the
> lexical var special doesn't turn it into a global variable (i.e., a
> symbol's value slot)? If anyone could enlighten me here?

Following-up to myself once more (sigh), CLTL2 tells the reason (the
HyperSpec was a bit terse in that regard...):

"symbol-value returns the current value of the dynamic (special)
variable named by symbol. An error occurs if the symbol has no value"

So it isn't just accessing the symbol's value slot, which I mistakenly
thought...
From: Kent M Pitman
Subject: Re: Lexical scope question
Date: 
Message-ID: <uwsx5dn8y.fsf@nhplace.com>
Matthias Buelow <···@incubus.de> writes:

> I wrote:
> 
> > Actually, I'm somewhat puzzled as to why (symbol-value 'var) works
> > (which it apparently does, at least in clisp)... I mean, declaring the
> > lexical var special doesn't turn it into a global variable (i.e., a
> > symbol's value slot)? If anyone could enlighten me here?
> 
> Following-up to myself once more (sigh), CLTL2 tells the reason (the
> HyperSpec was a bit terse in that regard...):
> 
> "symbol-value returns the current value of the dynamic (special)
> variable named by symbol. An error occurs if the symbol has no value"
> 
> So it isn't just accessing the symbol's value slot, which I mistakenly
> thought...

It certainly is accessing the symbol's value slot.  Those are just the
same thing.  The symbol's value gets a value stored into it.  When you
dynamic bind something, it's as if you did:

  (let ((old-value (symbol-value var)))
    (unwind-protect (progn (setf (symbol-value var) bound-value)
                           (evaluate-body-of-binding-form))
      (setf (symbol-value var) bound-value)))

except that it's generally done in a way that this magic is undone on
process switches, so it's not really unwind-protect, which is not going
to be threadsafe.  But the real point is that while you're in the body
of the binding form, symbol-value does return the dynamic value AND
the symbol's value cell holds that value.
  
Btw, on the issue of the relation of CLTL and ANSI CL...

Textually, ANSI CL arose as CLTL with a LOT of editing, begun by my
predecessor editor [Kathy Chapman] and continued by me.  At some
point, Steele declared that for copyright purposes, he was content to
say that there was no lingering relationship between the two documents
and that it was not necessary to regard one as a derivative work of
the other.  But sentences in CLTL generally did not get lost unless
they could be more or less proven to have no lingering value.  Rather,
they got moved (and sometimes consolidated).  And, of course, new
presentations were created for things when there was a better
presentation.  The principle thing that got "lost" was the order of
presentation, so things tried to be in the right place for reference,
not for explanation.  They also tried to be non-redundant--it was bad
to say the same thing twice, just in case we said it wrong in one place
and created a conflict in meaning.

The glossary definition for symbol value is where I would have guessed
a detail would have been "moved". I didn't find it there, so I broke up
the phrase into component parts and looked up value.  Indeed, there
it is:

 value n.
  ...
  3. (of a symbol) the value of the dynamic variable named by that symbol. 
  ...

Ref: http://www.lispworks.com/documentation/HyperSpec/Body/26_glo_v.htm

You can also look under the SYMBOL dictionary entry, where it talks about
the value.

  If a symbol has a value attribute, it is said to be bound, and that
  fact can be detected by the function boundp. The object contained in
  the value cell of a bound symbol is the value of the global variable
  named by that symbol, and can be accessed by the function
  symbol-value. A symbol can be made to be unbound by the function
  makunbound.
  
Ref: http://www.lispworks.com/documentation/HyperSpec/Body/t_symbol.htm#symbol

You can then look to the glossary for "global variable" and find:

 global variable n.
  a dynamic variable or a constant variable. 
  
Ref: http://www.lispworks.com/documentation/HyperSpec/Body/26_glo_g.htm#global_variable

And you can track through that to dynamic variable:

 dynamic variable n.
  a variable the binding for which is in the dynamic environment. See special. 

Ref: http://www.lispworks.com/documentation/HyperSpec/Body/26_glo_d.htm#dynamic_variable

It's true that in SYMBOL-VALUE itself, it just says:

  symbol---a symbol that must have a value. 
  ...  
  Accesses the symbol's value cell. 
  
Ref: http://www.lispworks.com/documentation/HyperSpec/Body/f_symb_5.htm#symbol-value

Now, I guess you could say the definition of symbol-value itself was terse.
But I'd call it modular.  And it is cross-indexed.  It clearly identifies
by the use of glossary font that these definitions are waiting for you to
flip to them.  The information is therefore not missing, and an affordance
is made to it.  There's a loss of locality, but a gain in meaning, given that
one doesn't have to know to turn to SYMBOL-VALUE to learn about how a symbol
works.

It's ok if you don't like the style.  But I didn't want to leave you with 
the impression that one document has the info and one doesn't.  It's just
differently placed and presented.

Indeed, the source TeX is relatively meticulous as the text moved around
to leave backpointers to where in CLTL something came from, or what issue
something came from, so that when challenged we could have half a chance
of saing why something was there.  (The issue stuff was marked in a 
mechanically recoverable way, which is why I was able to turn it into issue
cross-references in the program I wrote to turn the TeX into HTML 
(turning ANSI CL's spec into CLHS). The CLTL back-pointers were less formal,
so it wasn't as easiliy recoverable.)
  
And, of course, CLTL2 was never involved in the standards work.  CLTL
was a design-committee product. CLTL2 is an unblessed derivative of
CLTL, which Steele did privately. Both CLTL2 and ANSI CL have a common
parent, CLTL.  CLTL2 was a private attempt to express the intermediate
state of the ANSI CL process, but since we backed out of some of the
things that ended in CLTL2, it is conceptually skewed, not a midpoint
between CLTL and ANSI CL.  Steele explains some of this in the preface
of CLTL2, but since ANSI CL wasn't out yet, you have to read between
the lines as to what could have (and did) happen subsequent to CLTL2
in order to see the manifest problem which was to him a
potential/hypothetical at publication time.  Some vendors then
compounded the issue by implementing CLTL2.  But even though widely
implemented, it was never taken by the full community as standard, I
think at least partly because the presentational style of CLTL2
(through its use of change bars, constantly showing the original CLTL
and then saying "no, that's not true any more") was unsuitable as a
serious ongoing standard.

(Yeah, I've said some of this before.  I suppose I should just have
googled and pointed to it....)
From: Matthias Buelow
Subject: Re: Lexical scope question
Date: 
Message-ID: <5foamoF3bv3lpU1@mid.dfncis.de>
Kent M Pitman wrote:

> It certainly is accessing the symbol's value slot.  Those are just the
> same thing.  The symbol's value gets a value stored into it.  When you
> dynamic bind something, it's as if you did:
> 
>   (let ((old-value (symbol-value var)))
>     (unwind-protect (progn (setf (symbol-value var) bound-value)
>                            (evaluate-body-of-binding-form))
>       (setf (symbol-value var) bound-value)))
> 
> except that it's generally done in a way that this magic is undone on
> process switches, so it's not really unwind-protect, which is not going
> to be threadsafe.  But the real point is that while you're in the body
> of the binding form, symbol-value does return the dynamic value AND
> the symbol's value cell holds that value.

Wouldn't that be the old discussion of shallow vs. deep binding? That
is, in shallow binding, the symbol's value slot is set and the old
values stored in the call frames, and restored on backing up, whereas in
deep binding, the new values are stored in a stack-like manner, and the
symbol's value slot is left alone?
From: Kent M Pitman
Subject: Re: Lexical scope question
Date: 
Message-ID: <ufy3sncqa.fsf@nhplace.com>
Matthias Buelow <···@incubus.de> writes:

> Kent M Pitman wrote:
> 
> > It certainly is accessing the symbol's value slot.  Those are just the
> > same thing.  The symbol's value gets a value stored into it.  When you
> > dynamic bind something, it's as if you did:
> > 
> >   (let ((old-value (symbol-value var)))
> >     (unwind-protect (progn (setf (symbol-value var) bound-value)
> >                            (evaluate-body-of-binding-form))
> >       (setf (symbol-value var) bound-value)))
> > 
> > except that it's generally done in a way that this magic is undone on
> > process switches, so it's not really unwind-protect, which is not going
> > to be threadsafe.  But the real point is that while you're in the body
> > of the binding form, symbol-value does return the dynamic value AND
> > the symbol's value cell holds that value.
> 
> Wouldn't that be the old discussion of shallow vs. deep binding? That
> is, in shallow binding, the symbol's value slot is set and the old
> values stored in the call frames, and restored on backing up, whereas in
> deep binding, the new values are stored in a stack-like manner, and the
> symbol's value slot is left alone?

Well, I meant to side-step that.  It's certainly true that you can
implement it the other way.  It's beyond the scope of the standard, of
course.  All I really meant to do in the above was to say that it
suffices to say that this code above suffics as an explanation of how
symbol value and special variable value could be the same, since the
OP seemed to be suggesting there was an intrinsic contradiction.

I prefer to think of shallow/deep as an efficiency issue, at least for
CL, where there are no operators in the standard to detect the difference
via anything other than timing effects.
From: Matthias Buelow
Subject: Re: Lexical scope question
Date: 
Message-ID: <5fob4rF3d0h0rU1@mid.dfncis.de>
Kent M Pitman wrote:

> It's ok if you don't like the style.  But I didn't want to leave you with 
> the impression that one document has the info and one doesn't.  It's just
> differently placed and presented.

I didn't want to imply that the HyperSpec was defective :) I'm well
aware that standards documents are a lot more terse than uhm, more
descriptive books, like cltl2. That's why I generally prefer cltl2,
especially for the concepts, even though it doesn't describe the same
language as the ANSI specification.
From: Kent M Pitman
Subject: Re: Lexical scope question
Date: 
Message-ID: <ubqegnc5h.fsf@nhplace.com>
Matthias Buelow <···@incubus.de> writes:

> Kent M Pitman wrote:
> 
> > It's ok if you don't like the style.  But I didn't want to leave you with 
> > the impression that one document has the info and one doesn't.  It's just
> > differently placed and presented.
> 
> I didn't want to imply that the HyperSpec was defective :) I'm well
> aware that standards documents are a lot more terse than uhm, more
> descriptive books, like cltl2. That's why I generally prefer cltl2,
> especially for the concepts,

I certainly would agree with you on the hardcopy versions side by
side.  Although I used to refer to the document as hypertext even when
I was writing the hardcopy [since I'd implemented a hypertext editor
years before and had that notion in my head structurally], it was
quite fun to see CLHS come up the first time and see those things
light up.  In the hypertext, my personal feeling is that I'd much
rather be able to click on a term and get to its glossary meaning than
have to find it in CLTL2.  It's certainly true that CLTL2 has _some_
explanations that are more "locally coherent".  But it's spotty.
There are lots of definitions that are hard to find for exactly the
same reason.  For example, several very basic concepts about filenames
are buried in the middle of pathname functions, in ways that make you
wonder "are these local definitions that only apply to that concept as
viewed here in this definition, or am I to infer that these concepts
transfer to other functions with similar argument names, or to type
type itself?"  I gotta say, the ANSI CL chapter on pathnames isn't
hugely better, because there was more untangling I had on my list to
do when we just ran out of budget and froze things. I was pretty sad
about the final form of that chapter.  But overall, my personal belief
is that a hyperspec user is going to find a piece of reference info
faster than a cltl2 user, even using the online CLTL2, just because
there are more wormholes through its fabric of textual space that you
can teleport through.  But if you mean as a textual read for someone
just trying to bootstrap a vague understanding, yeah, that's probably
true.

> even though it doesn't describe the same
> language as the ANSI specification.

Yeah, there is that... ;)

My feelings on this are already summed up in my remarks about
the meeting where we discussed renaming DEFINE-SETF-METHOD in a way
that would break compatibility with CLTL2 ... See more details in:

http://groups.google.com/group/comp.lang.lisp/msg/6d55cc1fffb42bbe?hl=en&
From: Osei
Subject: Re: Lexical scope question
Date: 
Message-ID: <1184445429.060919.251080@k79g2000hse.googlegroups.com>
On Jul 12, 9:09 pm, Kent M Pitman <······@nhplace.com> wrote:
> Rainer Joswig <······@lispmachine.de> writes:
> > In article <·······················@57g2000hsv.googlegroups.com>,
> >  Osei <·········@gmail.com> wrote:
>
> > > > Don't hesitate to ask. You wrote some code and
> > > > you described what you thought it should do.
> > > > That's how I (we?) like newbies to ask those questions. ;-)
> > > > Understanding the difference between dynamic and
> > > > lexical binding is quite important if you want to
> > > > understand programming in Common Lisp. Other important
> > > > concepts are evaluation, macros, recursion and so on...
>
> > > Thanks.  This isn't so scary after all :)
>
> > > Since you insist... more questions (I finished and hopefully
> > > understood that article)
> > > Given...
>
> > > (defun inner () (format t "~A~%" var))
>
> > > (defun outer1 ()
> > >   (let ((var "dynamic"))
> > >      (declare (special var))   ; because of this DECLARE
> > >      (inner)                                ; this will use dynamic
> > > binding of var correctly
> > > ))
>
> > > (outer1) prints "dynamic\n"
>
> > > what i really want to do is to get the same output with the ff...
>
> > > (defun outer2 ()
> > >   (let ((var "dynamic"))
> > >      (declare (special var))
> > >      (lambda () (inner))
> > > ))
>
> > > I want to do
>
> > > (funcall (outer2))
>
> > > and get the same output but  this is an error since the dynamic
> > > binding of var is lost outside of OUTER2.
>
> > > Is there any way to call the lambda function
>
> Terminology:  It's not a lambda function.  It's an anonymous function.
>
> There are lambda expressions, which are (lambda (x) x).
> Those are forms, not values.  As values, they are lists, not functions.
>
> There are lambda combinations, which CL also calls lambda forms,
> which are ((lambda (x) x) 3).   These are also forms, not values.
> As values, they are again just lists.
>
> A function is what results from these.  It has no more use of LAMBDA
> and more than (A B C) has parens in it after it's been through the reader
> or any more than (* 3 4) is a "times" number after the multiplication is done
> and 12 is returned.  It's not a times 12.  It's just a twelve.
>
> (lambda (x) x) returns a function, not a lambda function.
> Before it is a lambda function, it is a list whose car is lambda,
> [possible to view as a form whose operator is the name of the LAMBDA
> macro].
>
> > > outside outer2 and still get the binding it had inside
>
> You're asking to remember a value that had been dynamic by effectively
> snapshotting it.  See last my example, OUTER4, below.
>
> > > or do I have to define INNER using FLET
> > > inside OUTER2.
>
> No.
>
> > > I hope this is clear.
>
> It is if I've answered your question, and it's not if I haven't.
> Heh.
>
> > > Osei
>
> > At runtime, the LAMBDA function
>
> Anonymous function resulting from the lambda expression.
>
> > will be called and there is no binding
> > for VAR. So you would need to introduce one. You can move the LET
> > into the LAMBDA function:
>
> > (defun outer2 ()
> >   (lambda ()
> >     (let ((var "dynamic"))
> >       (declare (special var))
> >       (inner))))
>
> Which is, of course, the same as, and probably slower than:
>
>  (defun outer3 ()
>    (lambda ()
>      (inner3 var)))
>
>  (defun inner3 (&optional (var (symbol-value 'var)))
>    (format t "~A~%" var))
>
> I think the idiom Osei is looking for is:
>
>  (defun outer4 ()
>    (let ((var "dynamic"))
>      (declare (special var))
>      (inner4)))
>
>  (defun inner4 ()
>    (let ((var (symbol-value 'var))) ;capture a dynamic value as a static value
>      #'(lambda () (write-line var))))
>
>  (funcall (outer4))
>  dynamic
>  => "dynamic"
>
> You could also write inner4 as having
>
>  (let ((var (locally
>               (declare (special var))
>               var)))
>    ...)
>
> if you didn't want to admit to yourself that (symbol-value 'var)
> is the same as (locally (declare (special var)) var).

I realize that this is *exactly* the idiom I am looking for.  Thanks.
From: Matthias Buelow
Subject: Re: Lexical scope question
Date: 
Message-ID: <5fo1imF3d7u9oU1@mid.dfncis.de>
Osei wrote:

> (defun outer2 ()
>   (let ((var "dynamic"))
>      (declare (special var))
>      (lambda () (inner))
> ))
> 
> I want to do
> 
> (funcall (outer2))
> 
> and get the same output but  this is an error since the dynamic
> binding of var is lost outside of OUTER2.

What the declaration does is make the variable "special" -- but only for
its lifetime ("dynamic extent"). When the variable is "live", references
from anywhere can be made to it ("indefinite scope"). When control
leaves the lexical block in which the variable is defined, the variable
goes out of scope and isn't visible anymore.

You can imagine it being implemented in some kind of stack; normal
lexical variables are often allocated on the program's stack (cf. to the
C language, where automatic variables are also usually stored on the
stack). If it is made "special", one additional thing is being done --
the variable allows stack-like updates (they might be put on the stack
or stored otherwise), and those updates are preserved across function
calls. For example, a function might walk down its stack to find the
latest update for a dynamic variable. If the control however leaves the
frame where the variable is defined, any reference to it can't find the
variable or any updates anymore on the stack -- they all have been
popped off by now, and it would consult the global environment, where in
your example the symbol's value slot is unbound, and hence the error.

What you could do is use a global (special) variable, define inner in
the lexical environment (which would make outer return a closure, that
is, the lexical variable packaged with the function), or simply pass the
data on as an argument to inner, depending on your application.

Scope and Extent is well explained in CLTL2, have a look at, for
example,
http://www.cs.cmu.edu/Groups/AI/html/cltl/clm/node43.html#SECTION00700000000000000000
From: Osei
Subject: Re: Lexical scope question
Date: 
Message-ID: <1184297815.723989.278020@g4g2000hsf.googlegroups.com>
On Jul 12, 9:07 pm, Matthias Buelow <····@incubus.de> wrote:
> Osei wrote:
> > (defun outer2 ()
> >   (let ((var "dynamic"))
> >      (declare (special var))
> >      (lambda () (inner))
> > ))
>
> > I want to do
>
> > (funcall (outer2))
>
> > and get the same output but  this is an error since the dynamic
> > binding of var is lost outside of OUTER2.
>
> What the declaration does is make the variable "special" -- but only for
> its lifetime ("dynamic extent"). When the variable is "live", references
> from anywhere can be made to it ("indefinite scope"). When control
> leaves the lexical block in which the variable is defined, the variable
> goes out of scope and isn't visible anymore.
>
> You can imagine it being implemented in some kind of stack; normal
> lexical variables are often allocated on the program's stack (cf. to the
> C language, where automatic variables are also usually stored on the
> stack). If it is made "special", one additional thing is being done --
> the variable allows stack-like updates (they might be put on the stack
> or stored otherwise), and those updates are preserved across function
> calls. For example, a function might walk down its stack to find the
> latest update for a dynamic variable. If the control however leaves the
> frame where the variable is defined, any reference to it can't find the
> variable or any updates anymore on the stack -- they all have been
> popped off by now, and it would consult the global environment, where in
> your example the symbol's value slot is unbound, and hence the error.
>
> What you could do is use a global (special) variable, define inner in
> the lexical environment (which would make outer return a closure, that
> is, the lexical variable packaged with the function), or simply pass the
> data on as an argument to inner, depending on your application.
>
> Scope and Extent is well explained in CLTL2, have a look at, for
> example,http://www.cs.cmu.edu/Groups/AI/html/cltl/clm/node43.html#SECTION0070...

In a mushy, informal sort of way, this finally makes sense to me.
However, that was after reading Ron Garret's paper and reading the
wealth of knowledge in the various posts in this thread. This is a
very nice explanation.  I think my biggest misunderstanding was about
the execution path and visibility of variables during and after that.

I will read the CLTL2 section to hopefully strengthen this fledgling
understanding of mine.

In my app, I can't/don't want to change INNER (it is actually defined
in an external library which uses that special variable).  I just
wanted to bind the variable appropriately before calling INNER.   So
the following works for me:

(defun outer8 ()   ; i lost count which "outer" we were on
   (lambda ()
     (let ((myparam "dynamic"))
       (declare (special myparam))
       (inner))))

(funcall (outer8)) ->  "dynamic"  ; shazam

Thanks to all who assisted on this leg of my journey to
enlightenment :)

Osei
From: Thomas A. Russ
Subject: Re: Lexical scope question
Date: 
Message-ID: <ymi644onnb9.fsf@sevak.isi.edu>
Osei <·········@gmail.com> writes:

> 
> Thanks.  This isn't so scary after all :)
> 
> Since you insist... more questions (I finished and hopefully
> understood that article)
> Given...
> 
> (defun inner () (format t "~A~%" var))

OK, for true safety, this should declare var to be special as well:

(defun inner () 
  (declare (special var))
  (format t "~A~%" var))

Most lisp systems will assume var is special (and usually issue a
warning), but it is good practice to code to avoid warnings.

> (defun outer1 ()
>   (let ((var "dynamic"))
>      (declare (special var))   ; because of this DECLARE
>      (inner)                                ; this will use dynamic
> binding of var correctly
> ))
> 
> (outer1) prints "dynamic\n"

Which it does because (inner) is executed within the dynamic scope of
the binding of var to "dynamic".  Outside the dynamic scope of the let,
the special variable var has no value (i.e., it is unbound).

> what i really want to do is to get the same output with the ff...
> 
> (defun outer2 ()
>   (let ((var "dynamic"))
>      (declare (special var))
>      (lambda () (inner))
> ))

OK.  What this does is create a closure (over lexical variables) that
provides an environment for resolving references to free variables in
the lexical (textual) body of the LET form.  Since the lambda doesn't
have any variables, there is really no need to form a closure.

The variable var has a value during the execution of outer2, but once
the function returns, the dynamic value is on longer present and the
global, unbound value of var is present.

> I want to do
> 
> (funcall (outer2))

The lambda expression returned by (outer2) refers to a special variable
that is unbound at top level, so there is no value available for (inner)
to print.

> and get the same output but  this is an error since the dynamic
> binding of var is lost outside of OUTER2.
> 
> Is there any way to call the lambda function outside outer2 and still
> get the binding it had inside or do I have to define INNER using FLET
> inside OUTER2.

That would be one method.  But then you would be looking to get lexical
scope instead of dynamic scope.  Perhaps the following code will help
make this distinction clear?


(defun scope-test ()
  (let ((lex "inner-lexical")
        (dyn "inner-dynamic"))
    (declare (special dyn))
    (lambda () (format t "Lex = ~A    Dyn = ~A" lex dyn))))

(let ((lex "top-lexical")
      (dyn "top-dynamic"))
  (declare (special dyn))
  (funcall (scope-test)))


-- 
Thomas A. Russ,  USC/Information Sciences Institute
From: Rob Warnock
Subject: Re: Lexical scope question
Date: 
Message-ID: <IPGdnZMzNqCMGAXbnZ2dnUVZ_judnZ2d@speakeasy.net>
Thomas A. Russ <···@sevak.isi.edu> wrote:
+---------------
| Osei <·········@gmail.com> writes:
| > Is there any way to call the lambda function outside outer2 and still
| > get the binding it had inside or do I have to define INNER using FLET
| > inside OUTER2.
| 
| That would be one method.  But then you would be looking to get lexical
| scope instead of dynamic scope.  Perhaps the following code will help
| make this distinction clear?
| 
| (defun scope-test ()
|   (let ((lex "inner-lexical")
|         (dyn "inner-dynamic"))
|     (declare (special dyn))
|     (lambda () (format t "Lex = ~A    Dyn = ~A" lex dyn))))
| 
| (let ((lex "top-lexical")
|       (dyn "top-dynamic"))
|   (declare (special dyn))
|   (funcall (scope-test)))
+---------------

Sneaky! I was confused for a moment by the output
of that one until I actually read it correctly!  ;-}

The OP might also find the following version amusing:

  (defun scope-test ()
    (let ((lex "inner-lexical")
          (dyn "inner-dynamic"))
      (declare (special dyn))
      (flet ((do-print (n)
	       (format t "~d: Lex = ~A    Dyn = ~A~%" n lex dyn)))
	(do-print 1)
        #'do-print)))
 
  (let ((lex "top-lexical")
        (dyn "top-dynamic"))
    (declare (ignorable lex)		; muffle warning
	     (special dyn))
    (funcall (scope-test) 2))


-Rob

-----
Rob Warnock			<····@rpw3.org>
627 26th Avenue			<URL:http://rpw3.org/>
San Mateo, CA 94403		(650)572-2607