From: rodrigo vanegas
Subject: (setf (symbol-function)
Date: 
Message-ID: <RV.93Jun11234739@monaco.cs.brown.edu>
Are the following forms equivalent?

  1. (defun <symbol> () <body>)

  2. (setf (symbol-function '<symbol>) #'(lambda () <body>))

rodrigo vanegas
··@cs.brown.edu

From: rodrigo vanegas
Subject: Re: (setf (symbol-function)
Date: 
Message-ID: <RV.93Jun12144650@monaco.cs.brown.edu>
In article <················@monaco.cs.brown.edu>, ··@cs.brown.edu (rodrigo vanegas) writes:

> Are the following forms equivalent?

>   1. (defun <symbol> () <body>)

>   2. (setf (symbol-function '<symbol>) #'(lambda () <body>))

I've since dicovered that the forms

  1. (defun foo () "docstring" nil)

  2. (setf (symbol-function 'foo) #'(lambda () "docstring" nil))

have different effects.  Is there a way to remedy this situation?  In
other words, is there a method for creating functions during run-time
which also have a documentation string?


rodrigo vanegas
··@cs.brown.edu
From: Barry Margolin
Subject: Re: (setf (symbol-function)
Date: 
Message-ID: <1vec9dINN8bm@early-bird.think.com>
In article <················@monaco.cs.brown.edu> ··@cs.brown.edu (rodrigo vanegas) writes:
>other words, is there a method for creating functions during run-time
>which also have a documentation string?

(setf (symbol-function 'name) #'(lambda ...))
(setf (documentation 'name 'function) "docstring")
-- 
Barry Margolin
System Manager, Thinking Machines Corp.

······@think.com          {uunet,harvard}!think!barmar
From: Barry Margolin
Subject: Re: (setf (symbol-function)
Date: 
Message-ID: <1vdgtsINNlpe@early-bird.think.com>
In article <················@monaco.cs.brown.edu> ··@cs.brown.edu (rodrigo vanegas) writes:
>Are the following forms equivalent?
>  1. (defun <symbol> () <body>)
>  2. (setf (symbol-function '<symbol>) #'(lambda () <body>))

Yes, as far as the standard language is concerned.  But many
implementations do extra stuff for DEFUN forms.  For instance, many
implementations remember the source file that defined a function, and this
is usually done by DEFUN but not SETF.  The DEFUN might also append to the
list of functions known to be defined, to suppress compile-time warnings
about calls to undefined functions, but the SETF often doesn't.

-- 
Barry Margolin
System Manager, Thinking Machines Corp.

······@think.com          {uunet,harvard}!think!barmar
From: Tim Moore
Subject: Re: (setf (symbol-function)
Date: 
Message-ID: <MOORE.93Jun14102410@defmacro.cs.utah.edu>
In article <············@early-bird.think.com> ······@think.com (Barry Margolin) writes:
   In article <················@monaco.cs.brown.edu> ··@cs.brown.edu (rodrigo vanegas) writes:
   >Are the following forms equivalent?
   >  1. (defun <symbol> () <body>)
   >  2. (setf (symbol-function '<symbol>) #'(lambda () <body>))

   Yes, as far as the standard language is concerned.  But many

No, not quite.  DEFUN encloses  <body> in an implicit block named
<symbol>, so you can (return-from <symbol> ...)

   -- 
   Barry Margolin
   System Manager, Thinking Machines Corp.

   ······@think.com          {uunet,harvard}!think!barmar

--
Tim Moore                    ·····@cs.utah.edu {bellcore,hplabs}!utah-cs!moore
"Wind in my hair - Shifting and drifting - Mechanical music - Adrenaline surge"
	- Rush
From: David Schulenburg
Subject: Re: (setf (symbol-function)
Date: 
Message-ID: <1viarb$945@news.aero.org>
In article <············@early-bird.think.com>, ······@think.com (Barry Margolin) writes:
|> In article <················@monaco.cs.brown.edu> ··@cs.brown.edu (rodrigo vanegas) writes:
|> >Are the following forms equivalent?
|> >  1. (defun <symbol> () <body>)
|> >  2. (setf (symbol-function '<symbol>) #'(lambda () <body>))
|> 
|> Yes, as far as the standard language is concerned.  But many
|> implementations do extra stuff for DEFUN forms.  For instance, many
|> implementations remember the source file that defined a function, and this
|> is usually done by DEFUN but not SETF.  The DEFUN might also append to the
|> list of functions known to be defined, to suppress compile-time warnings
|> about calls to undefined functions, but the SETF often doesn't.

this is actually incorrect.  from the dpANS:

"defun implicitly puts a block named block-name around the body forms (but
not the forms in the lambda-list) of the function defined." (p. 5-15)

this side effect does not take place in the second form above.

also, from the dpANS:

"Defines a new function named function-name in the global environment."
(p. 5-15)

from CLTL2:

"X3J13 voted in March 1989 <50> to clarify that, while defining forms
normally appear at top level, it is meaningful to place them in
non-top-level contexts; defun must define the function within the
enclosing lexical environment, not within the null lexical environment."
(p. 84)

these last two quotations seem to be at odds with one another.  isn't
the dpANS in error here?

david
From: Barry Margolin
Subject: Re: (setf (symbol-function)
Date: 
Message-ID: <20d09rINNmuk@early-bird.think.com>
In article <··········@news.aero.org> ········@Aero.org (David Schulenburg) writes:
>this is actually incorrect.  from the dpANS:
>
>"defun implicitly puts a block named block-name around the body forms (but
>not the forms in the lambda-list) of the function defined." (p. 5-15)
>
>this side effect does not take place in the second form above.

Right.  The correct equivalence should be:

(setf (symbol-function '<symbol>) #'(lambda () (block <symbol> <body>)))

>also, from the dpANS:
>
>"Defines a new function named function-name in the global environment."
>(p. 5-15)
>
>from CLTL2:
>
>"X3J13 voted in March 1989 <50> to clarify that, while defining forms
>normally appear at top level, it is meaningful to place them in
>non-top-level contexts; defun must define the function within the
>enclosing lexical environment, not within the null lexical environment."
>(p. 84)
>
>these last two quotations seem to be at odds with one another.  isn't
>the dpANS in error here?

No, but I can see how the poor wording can confused you.  The function name
is always defined in the global environment, but the function body is
executed in the enclosing lexical environment.  Here's an example that
demonstrates the difference:

> (let ((a 10))
    (flet ((bar (b))
	     (+ a b))
      (defun bar (c)
	(- a c))
      (bar 10)))
13
> (bar 10)
-7

Executing the first form invoked the lexical BAR, but it also defined a
global BARf as a side effect.  The global BAR's body is a lexical closure
in the environment of the LET, so it remembers the value of the lexical
variable A.

If you expand the DEFUN into the above SETF, this rule is obvious.
However, many compiler implementations try to special-case DEFUN, and these
special cases didn't work for lexically-enclosed DEFUNs, and they would
either ignore the lexical environment or refuse to compile such files (some
less onerous implementations would simply leave the non-top-level functions
in interpreted form).  The intent of the clarification (note that it was
*not* classified as a change to the language) was to remind implementors
that these short-cuts are not permitted; non-top-level DEFUNs have to be
handled properly.
-- 
Barry Margolin
System Manager, Thinking Machines Corp.

······@think.com          {uunet,harvard}!think!barmar