Account Options

  1. Sign in
The old Google Groups will be going away soon, but your browser is incompatible with the new version.
Google Groups Home
« Groups Home
Anaphoric macros and packages
There are currently too many topics in this group that display first. To make this topic appear first, remove this option from another topic.
There was an error processing your request. Please try again.
flag
  16 messages - Collapse all  -  Translate all to Translated (View all originals)
The group you are posting to is a Usenet group. Messages posted to this group will make your email address visible to anyone on the Internet.
Your reply message has not been sent.
Your post was successful
 
From:
To:
Cc:
Followup To:
Add Cc | Add Followup-to | Edit Subject
Subject:
Validation:
For verification purposes please type the characters you see in the picture below or the numbers you hear by clicking the accessibility icon. Listen and type the numbers you hear
 
Gabor Melis  
View profile  
 More options Dec 4 2002, 6:02 am
Newsgroups: comp.lang.lisp
From: m...@hotpop.com (Gabor Melis)
Date: 4 Dec 2002 03:02:34 -0800
Local: Wed, Dec 4 2002 6:02 am
Subject: Anaphoric macros and packages
In Paul Graham's On Lisp, there is a chapter dedicated to anaphoric
macros. One of the simplest ones is 'aif' that binds 'it' to the value
of the condition evaluated in an 'if':

(defmacro aif (test-form then-form &optional else-form)
  `(let ((it ,test-form))
     (if it ,then-form ,else-form)))

;;; example
(aif 5
  (print it))

Now, it works fine if the macro definition and expansion are done in
the same package, but falls on its face when not:

;;; package 1 with the macro def
(cl:defpackage "P1"
  (:use "COMMON-LISP")
  (:export "AIF"))

(in-package "P1")

(defmacro aif (test-form then-form &optional else-form)
  `(let ((it ,test-form))
     (if it ,then-form ,else-form)))

;;; package 2 that uses the macro
(cl:defpackage "P2"
  (:use "COMMON-LISP")
  (:use "P1"))

(in-package "P2")

;;; example
(aif 5
  (print it))

Loading this file in clisp (v2.27) results in:
*** - EVAL: variable IT has no value
and macroexpand-1 says that (aif 5 (print it)) is expanded to:
(LET ((P1::IT 5)) (IF P1::IT (PRINT IT) NIL))

P1::IT???
If I do a 'compile-defun-lisp' by hand in emacs for all toplevel
s-exps it works.

What did I do wrong?

Cheers, Gabor


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Frode Vatvedt Fjeld  
View profile  
 More options Dec 4 2002, 6:18 am
Newsgroups: comp.lang.lisp
From: Frode Vatvedt Fjeld <fro...@cs.uit.no>
Date: Wed, 04 Dec 2002 12:18:41 +0100
Local: Wed, Dec 4 2002 6:18 am
Subject: Re: Anaphoric macros and packages

m...@hotpop.com (Gabor Melis) writes:
> What did I do wrong?

Forget to export the symbol "it" from P1?

--
Frode Vatvedt Fjeld


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Arthur Lemmens  
View profile  
 More options Dec 4 2002, 6:26 am
Newsgroups: comp.lang.lisp
From: Arthur Lemmens <alemm...@xs4all.nl>
Date: Wed, 04 Dec 2002 12:24:20 +0100
Local: Wed, Dec 4 2002 6:24 am
Subject: Re: Anaphoric macros and packages

Gabor Melis wrote:

> In Paul Graham's On Lisp, there is a chapter dedicated to anaphoric
> macros. One of the simplest ones is 'aif' that binds 'it' to the value
> of the condition evaluated in an 'if':

> (defmacro aif (test-form then-form &optional else-form)
>   `(let ((it ,test-form))
>      (if it ,then-form ,else-form)))
> Now, it works fine if the macro definition and expansion are done in
> the same package, but falls on its face when not:

Yes. That's one reason why some people (me included) prefer something like
WHEN-LET:

  (defmacro when-let ((var test-form) &body body)
    `(let ((,var ,test-form))
       (when ,var ,@body)))

  ;; Example:
  (when-let (it (hairy-computation))
    (print it))

> What did I do wrong?

Nothing, really. But I think that Paul Graham did something wrong with
the design of AIF.

Arthur Lemmens


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Gabor Melis  
View profile  
 More options Dec 4 2002, 12:45 pm
Newsgroups: comp.lang.lisp
From: m...@hotpop.com (Gabor Melis)
Date: 4 Dec 2002 09:45:24 -0800
Local: Wed, Dec 4 2002 12:45 pm
Subject: Re: Anaphoric macros and packages

Arthur Lemmens <alemm...@xs4all.nl> wrote in message <news:3DEDE5E4.A9A8EA97@xs4all.nl>...
> Gabor Melis wrote:
> > What did I do wrong?

> Nothing, really. But I think that Paul Graham did something wrong with
> the design of AIF.

OK. I am feeling better, but I need to know why it doesn't work. It
looks right. And it works right if I do the compile-defun-lisp trick
in the original post.

 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Simon András  
View profile  
 More options Dec 4 2002, 1:40 pm
Newsgroups: comp.lang.lisp
From: asi...@math.bme.hu (Simon András)
Date: 04 Dec 2002 20:40:31 +0100
Local: Wed, Dec 4 2002 2:40 pm
Subject: Re: Anaphoric macros and packages

m...@hotpop.com (Gabor Melis) writes:
> OK. I am feeling better, but I need to know why it doesn't work. It

Have you tried following Frode's advice and export the symbol IT
along with AIF from the P1 package? The double colon in the
macroexpansion is telling.

Andras


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Erik Naggum  
View profile  
 More options Dec 4 2002, 6:37 pm
Newsgroups: comp.lang.lisp
From: Erik Naggum <e...@naggum.no>
Date: 04 Dec 2002 23:37:10 +0000
Local: Wed, Dec 4 2002 6:37 pm
Subject: Re: Anaphoric macros and packages
* Gabor Melis
| What did I do wrong?

  You used a poorly designed feature.

  The key here is to get a short-hand for

(let ((expr (whatever)))
  (when expr
    (something-using-expr)))

  but in the tradition of really badly designed languages, an implicit
  binding is used instead of doing explicit bindings in the Common Lisp
  tradition, which would also allow more than one binding/expression.

  I would much prefer a syntax like this:

(whereas ((expr-1 (whatever-1))
          (expr-2 (whatever-2)))
  (something-using-expr-1-and/or-expr-2))

  Reading it like the standard contract legalese, the key idea is that all
  prior forms are true when an expression in the binding forms is evaluated
  (just like the operator `and´) and prior variable are bound to the (true)
  value of each prior expression.  The body is an implicit `progn´ that can
  thus rely on all of these forms having non-nil values.

  Having exhausted all useful things to do, I, too, have been thinking about
  how to do bindings and declarations more conveniently, and, not being the
  least bit afraid of parentheses, have decided on binding forms that have
  the general structure

(var-list [expression [decl-list]])

  where var-list is a designator for a list of (symbols naming) variables,
  expression may return multiple values bound to those variables with the
  standard nil default, and decl-list is a designator for a list of types.
  To be gratuitously super-clever, if the type of a variable in `whereas´
  is an explicit union of `null´ and something else to signal that `nil´ is
  a valid value, the result of the test is that using the succeeding value
  (etc by induction) and if it is the last value, the entire form is used
  for bindings, only.  Some examples may yet have a slightly illuminating
  effect:

(whereas (((value present-p) (gethash ...) ((or null ...))))
  ;; value is now actually obtained from the hashtable
  ...)
= (multiple-value-bind (value present-p) (gethash ...)
     (declare (type (or null ...) value))
     (when present-p
       ...)))

(whereas ((index (position ...) fixnum))
  ;; index now holds a fixnum index of an element actually in the sequence
  ...)
= (let ((index (position ...)))
    (when index
      (locally (declare (fixnum index))
        ...)))

(whereas ((cell (assoc ...) cons)
          (value (cdr cell)))
  ;; cell now holds an actually matching cons cell from the alist
  )
= (let ((cell (assoc ...)))
    (when cell
      (locally (declare (cons cell))
        (let ((value (cdr cell)))
          (when value
            ...)))))

  My `let´ and other binding forms parallel this development with a final
  (additional) argument that is the declared types, and allow a list of
  variables for binding multiple values.  Required arguments in lambda
  lists may be typed just like methods on generic functions.  The amount of
  effort to get this done is surprisingly small, and making it fully
  backward-compatible is almost easier than breaking things.

  Please remember that the purpose of this stunt is to give people a good
  reason to stay away from ill-designed and very un-Common-Lispy ways of
  "improving" on the language.  Macros that bind things and which neither
  work when nested nor when naïvely exported in the package system may
  appear "cool" to people who come from other languages, but not to the
  seasoned users.  Just like some may believe that "then" and "else" have a
  place in `if´ "statements" because the language they /really/ want to use
  does that, misguided attempts annoy people more than benefit a community.

--
Erik Naggum, Oslo, Norway

Act from reason, and failure makes you rethink and study harder.
Act from faith, and failure makes you blame someone and push harder.


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
JP Massar  
View profile  
 More options Dec 5 2002, 12:31 am
Newsgroups: comp.lang.lisp
From: mas...@alum.mit.edu (JP Massar)
Date: Thu, 05 Dec 2002 05:31:29 GMT
Local: Thurs, Dec 5 2002 12:31 am
Subject: Re: Anaphoric macros and packages
On 4 Dec 2002 03:02:34 -0800, m...@hotpop.com (Gabor Melis) wrote:

The fact that you question why it is P1::IT instead of
(what?  P2::IT ?) says to me you need to understand about
how the Lisp Reader works, how INTERN works and how it
interacts with the Lisp Reader, and perhaps how macro expansion
works.

Briefly, the 'IT' is seen by the reader and turned into a
symbol in the P1 package by the reader (because you did an
'in-package' to P1).  The defmacro 'really' looks like

(lisp::defmacro p1::aif (...)
  `(lisp::et ((p1::it ,p1::test-form))
   ...
   )

after it is read in.  

The 'IT' in (aif 5 (print it)) after you do (in-package "P2")
is likewise really p2::it, and these two symbols have
absolutely nothing to do with one another.

Does this help?

>If I do a 'compile-defun-lisp' by hand in emacs for all toplevel
>s-exps it works.

Not sure why this is working for you.  I don't think it should.

 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Kenny Tilton  
View profile  
 More options Dec 5 2002, 1:23 am
Newsgroups: comp.lang.lisp
From: Kenny Tilton <ktil...@nyc.rr.com>
Date: Thu, 05 Dec 2002 06:19:25 GMT
Local: Thurs, Dec 5 2002 1:19 am
Subject: Re: Anaphoric macros and packages

Gabor Melis wrote:
> Arthur Lemmens <alemm...@xs4all.nl> wrote in message <news:3DEDE5E4.A9A8EA97@xs4all.nl>...

>>Gabor Melis wrote:

>>>What did I do wrong?

>>Nothing, really. But I think that Paul Graham did something wrong with
>>the design of AIF.

> OK. I am feeling better, but I need to know why it doesn't work. It
> looks right. And it works right if I do the compile-defun-lisp trick
> in the original post.

Slow down. It does /not/ look right.[1] Graham did not have different
packages. You added different packages. When tou change shit and shit
breaks, dwell first on the changes you made. Packages.

Did you really want to master packages and macros at /the same time/?
Brave soul! :)

If so, its simple: symbols "coded" by a macro, while reasonably viewed
to be expanded into the code where the macro is coded, do /not/ in fact
invade the namespace of a /different/ package of the code referencing
the macro, as would code actually written there.

So by default "it" does not invade the namespace of package P2. Even if
P2 "uses" P1. But! If P1 exports "it", the body of code provided to AIF
will "see" the "it" provided by p1.

[1] I have no idea why an emacs compile-defun-lisp
  "trick" makes it work, i don't happen to do emacs. i do know truly
interpreted shit works where compiled doesn't (why I do not know) so
maybe you are in this area.

--

  kenny tilton
  clinisys, inc
  ---------------------------------------------------------------
""Well, I've wrestled with reality for thirty-five years, Doctor,
   and I'm happy to state I finally won out over it.""
                                                   Elwood P. Dowd


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Kenny Tilton  
View profile  
 More options Dec 5 2002, 1:26 am
Newsgroups: comp.lang.lisp
From: Kenny Tilton <ktil...@nyc.rr.com>
Date: Thu, 05 Dec 2002 06:22:44 GMT
Local: Thurs, Dec 5 2002 1:22 am
Subject: Re: Anaphoric macros and packages

Frode Vatvedt Fjeld wrote:
> m...@hotpop.com (Gabor Melis) writes:

>>What did I do wrong?

> Forget to export the symbol "it" from P1?

Jeez, could you be more terse? The guy's a newbie, maybe you could cut
it down to two words: "Export 'it'?" Or were you just being pedantic?

:)

--

  kenny tilton
  clinisys, inc
  ---------------------------------------------------------------
""Well, I've wrestled with reality for thirty-five years, Doctor,
   and I'm happy to state I finally won out over it.""
                                                   Elwood P. Dowd


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Thomas F. Burdick  
View profile  
 More options Dec 5 2002, 2:16 am
Newsgroups: comp.lang.lisp
From: t...@earthquake.OCF.Berkeley.EDU (Thomas F. Burdick)
Date: 04 Dec 2002 23:16:21 -0800
Local: Thurs, Dec 5 2002 2:16 am
Subject: Re: Anaphoric macros and packages

Erik Naggum <e...@naggum.no> writes:
>   I would much prefer a syntax like this:

> (whereas ((expr-1 (whatever-1))
>           (expr-2 (whatever-2)))
>   (something-using-expr-1-and/or-expr-2))

BTW, Erik, this is fantastic.  I had was only somewhat satisfied with
my if-let macro (if-let (var expression) then [else]), and in fact, I
never use it.  I do use my binding-cond macro sometimes
(binding-cond var (expr form...) ...).  Yours is a cute name, but I
especially like the idea of having a full sequence of let forms
available.

>   Having exhausted all useful things to do, I, too, have been thinking about
>   how to do bindings and declarations more conveniently, and, not being the
>   least bit afraid of parentheses, have decided on binding forms that have
>   the general structure

> (var-list [expression [decl-list]])

Hey, great minds I guess (or bored or idle minds, maybe).  I have been
using:

  (vars-form [expression [&rest declarations]])
  vars-form ::= var | var-list
  var-list ::= (var-name ...)
  var-name ::= var | (var type)

Which is a little more complicated to implement, but pretty much the
same idea.  It makes type declarations easier than others, because I
use them far mor often than any other type of declaration.  I think
this form is even less for those afraid of parens, though:

  (tfb:let. ((((x integer) (y some-type)) (compute-values))
             (((z number)) (compute-more)))
    (foo x y z))

--
           /|_     .-----------------------.                        
         ,'  .\  / | No to Imperialist war |                        
     ,--'    _,'   | Wage class war!       |                        
    /       /      `-----------------------'                        
   (   -.  |                              
   |     ) |                              
  (`-.  '--.)                              
   `. )----'                              


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Frode Vatvedt Fjeld  
View profile  
 More options Dec 5 2002, 4:13 am
Newsgroups: comp.lang.lisp
From: Frode Vatvedt Fjeld <fro...@cs.uit.no>
Date: Thu, 05 Dec 2002 10:13:19 +0100
Local: Thurs, Dec 5 2002 4:13 am
Subject: Re: Anaphoric macros and packages

Kenny Tilton <ktil...@nyc.rr.com> writes:
> Jeez, could you be more terse? The guy's a newbie, maybe you could
> cut it down to two words: "Export 'it'?" Or were you just being
> pedantic?

I'm just a believer in letting people making their own mistakes, I
guess. I think the aif thingy is a big mistake, and the OP's trouble
with packages was just derailing him from a speedy arrival at the same
conclusion..

--
Frode Vatvedt Fjeld


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Rob Warnock  
View profile  
 More options Dec 5 2002, 6:47 am
Newsgroups: comp.lang.lisp
From: r...@rpw3.org (Rob Warnock)
Date: Thu, 05 Dec 2002 05:47:37 -0600
Local: Thurs, Dec 5 2002 6:47 am
Subject: Re: Anaphoric macros and packages
Arthur Lemmens  <alemm...@xs4all.nl> wrote:
+---------------
| But I think that Paul Graham did something wrong with the design of AIF.
+---------------

Note that ANSI CL itself already contains some anaphora:

        (let ((list '(nil (a b) nil (c d e) nil (f g h i) (j k l))))
          (loop for i in list
            when (third i)      ; pun intended.
             collect it))
        => (E H L)

-Rob

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


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Frode Vatvedt Fjeld  
View profile  
 More options Dec 5 2002, 6:53 am
Newsgroups: comp.lang.lisp
From: Frode Vatvedt Fjeld <fro...@cs.uit.no>
Date: Thu, 05 Dec 2002 12:53:21 +0100
Local: Thurs, Dec 5 2002 6:53 am
Subject: Re: Anaphoric macros and packages

r...@rpw3.org (Rob Warnock) writes:
> Note that ANSI CL itself already contains some anaphora:

>    (let ((list '(nil (a b) nil (c d e) nil (f g h i) (j k l))))
>      (loop for i in list
>        when (third i)      ; pun intended.
>         collect it))
>    => (E H L)

I don't think the "it" here is much more magical than the other loop
keywords. If you try "collect (identity it)", it won't work.

--
Frode Vatvedt Fjeld


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Gabor Melis  
View profile  
 More options Dec 5 2002, 9:37 am
Newsgroups: comp.lang.lisp
From: m...@hotpop.com (Gabor Melis)
Date: 5 Dec 2002 06:37:05 -0800
Local: Thurs, Dec 5 2002 9:37 am
Subject: Re: Anaphoric macros and packages

Yes. And the other replies helped, too. Even though the spec does not
imply it, for some reason I had the mental picture of the result of
the macro expansion being fed to the reader. Now, it seems clear how
it (doesn't) work(s) and why exporting IT helped.

And as a side-effect (should be avoided, I know :-)), anaphoric macros
lost some of their allure.

Thanks, Gabor


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Michael Hudson  
View profile  
 More options Dec 5 2002, 9:55 am
Newsgroups: comp.lang.lisp
From: Michael Hudson <m...@python.net>
Date: Thu, 5 Dec 2002 14:47:29 GMT
Local: Thurs, Dec 5 2002 9:47 am
Subject: Re: Anaphoric macros and packages
Frode Vatvedt Fjeld <fro...@cs.uit.no> writes:

> I don't think the "it" here is much more magical than the other loop
> keywords.

And, somewhat related to this thread, loop keywords are recognized by
symbol name and not identity.  I wonder if the first implementation of
loop did that?

This is what makes it possible to write them as keywords (in another
sense of the word...), something that makes them stand out nicely
(with font-lock, anyway)..

Cheers,
M.

--
  Richard Gabriel was wrong: worse is not better, lying is better.
  Languages and systems succeed in the marketplace to the extent that
  their proponents lie about what they can do.
                                       -- Tim Bradshaw, comp.lang.lisp


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Hannah Schroeter  
View profile  
 More options Dec 5 2002, 1:23 pm
Newsgroups: comp.lang.lisp
From: han...@schlund.de (Hannah Schroeter)
Date: 5 Dec 2002 18:23:15 GMT
Local: Thurs, Dec 5 2002 1:23 pm
Subject: Re: Anaphoric macros and packages
Hello!

Gabor Melis <m...@hotpop.com> wrote:
>[...]
>And as a side-effect (should be avoided, I know :-)), anaphoric macros
>lost some of their allure.

We're not so dogmatic wrt side effects on this side of the great
Scheme/CL divide. :-)

Kind regards,

Hannah.


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
End of messages
« Back to Discussions « Newer topic     Older topic »