Discussion:
Lisp 2's and function values.
Matthew D. Swank
2011-05-25 02:51:48 UTC
Permalink
Content preview: I have implemented a small fexpr interpreter in Common Lisp
based on Kernel http://web.cs.wpi.edu/~jshutt/kernel.html. Right now it's
a Lisp 1, but I am considering trying to make it a more idiomatic extension
of Common Lisp by making it a Lisp 2. [...]

Content analysis details: (-0.0 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
-0.0 RCVD_IN_DNSWL_NONE RBL: Sender listed at http://www.dnswl.org/, low
trust
[209.225.8.23 listed in list.dnswl.org]
-0.0 T_RP_MATCHES_RCVD Envelope sender domain matches handover relay
domain
-0.0 SPF_PASS SPF: sender matches SPF record
0.0 RFC_ABUSE_POST Both abuse and postmaster missing on sender domain
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/398>

I have implemented a small fexpr interpreter in Common Lisp based on
Kernel http://web.cs.wpi.edu/~jshutt/kernel.html. Right now it's a Lisp
1, but I am considering trying to make it a more idiomatic extension of
Common Lisp by making it a Lisp 2.

Part of the Lisp 2-ness of the Common Lisp evaluator is that the car of
a form must name a function, macro, or special form. This name is either
a symbol bound in the function name space, or a lambda expression.
However, Kernel just requires the car evaluate to a combiner (this is
what Kernel calls a generic operator). Obviously, in a Lisp 2, a symbol
would evaluate to the value bound to it in the function name space.
However, consider the following:

((returns-a-function) arg arg ...)

Would it be reasonable to allow this as a legal form as well?

I'm not arguing Common Lisp should work this way, but I seems to make
sense in the context of a Kernel like evaluator.

Matt
Pascal Costanza
2011-05-25 05:34:22 UTC
Permalink
Content preview: On 25 May 2011, at 04:51, Matthew D. Swank wrote: > I have
implemented a small fexpr interpreter in Common Lisp based on > Kernel http://web.cs.wpi.edu/~jshutt/kernel.html.
Right now it's a Lisp > 1, but I am considering trying to make it a more
idiomatic extension of > Common Lisp by making it a Lisp 2. > > Part of the
Lisp 2-ness of the Common Lisp evaluator is that the car of > a form must
name a function, macro, or special form. This name is either > a symbol bound
in the function name space, or a lambda expression. > However, Kernel just
requires the car evaluate to a combiner (this is > what Kernel calls a generic
operator). Obviously, in a Lisp 2, a symbol > would evaluate to the value
Post by Matthew D. Swank
((returns-a-function) arg arg ...) > > Would it be reasonable to allow
this as a legal form as well? > > I'm not arguing Common Lisp should work
this way, but I seems to make > sense in the context of a Kernel like evaluator.
[...]

Content analysis details: (-102.3 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
-100 USER_IN_WHITELIST From: address is in the user's white-list
-2.3 RCVD_IN_DNSWL_MED RBL: Sender listed at http://www.dnswl.org/, medium
trust
[134.184.129.112 listed in list.dnswl.org]
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/399>
Post by Matthew D. Swank
I have implemented a small fexpr interpreter in Common Lisp based on
Kernel http://web.cs.wpi.edu/~jshutt/kernel.html. Right now it's a Lisp
1, but I am considering trying to make it a more idiomatic extension of
Common Lisp by making it a Lisp 2.
Part of the Lisp 2-ness of the Common Lisp evaluator is that the car of
a form must name a function, macro, or special form. This name is either
a symbol bound in the function name space, or a lambda expression.
However, Kernel just requires the car evaluate to a combiner (this is
what Kernel calls a generic operator). Obviously, in a Lisp 2, a symbol
would evaluate to the value bound to it in the function name space.
((returns-a-function) arg arg ...)
Would it be reasonable to allow this as a legal form as well?
I'm not arguing Common Lisp should work this way, but I seems to make
sense in the context of a Kernel like evaluator.
_If_ (returns-a-function) indeed returns a function, then this could be ok. But what if it doesn't return a function? What if it is a macro that returns just a symbol? Do you want to risk that ((return-something) ...) has a different meaning than (funcall (return-something) ...)? This is potentially confusing and could lead to code that is hard to debug...

Pascal

--
Pascal Costanza
The views expressed in this email are my own, and not those of my employer.
Martin Simmons
2011-05-25 11:45:20 UTC
Permalink
Content preview: >>>>> On Wed, 25 May 2011 07:34:22 +0200, Pascal Costanza
said: > > On 25 May 2011, at 04:51, Matthew D. Swank wrote: > > > I have implemented
a small fexpr interpreter in Common Lisp based on > > Kernel http://web.cs.wpi.edu/~jshutt/kernel.html.
Right now it's a Lisp > > 1, but I am considering trying to make it a more
idiomatic extension of > > Common Lisp by making it a Lisp 2. > > > > Part
of the Lisp 2-ness of the Common Lisp evaluator is that the car of > > a
form must name a function, macro, or special form. This name is either > >
a symbol bound in the function name space, or a lambda expression. > > However,
Kernel just requires the car evaluate to a combiner (this is > > what Kernel
calls a generic operator). Obviously, in a Lisp 2, a symbol > > would evaluate
to the value bound to it in the function name space. > > However, consider
the following: > > > > ((returns-a-function) arg arg ...) > > > > Would it
be reasonable to allow this as a legal form as well? > > > > I'm not arguing
Common Lisp should work this way, but I seems to make > > sense in the context
of a Kernel like evaluator. > > _If_ (returns-a-function) indeed returns
a function, then this could be > ok. But what if it doesn't return a function?
What if it is a macro that > returns just a symbol? Do you want to risk that
((return-something) ...) has > a different meaning than (funcall (return-something)
...)? This is > potentially confusing and could lead to code that is hard
to debug... [...]

Content analysis details: (-0.0 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
0.0 SINGLE_HEADER_2K A single header contains 2K-3K characters
-0.0 T_RP_MATCHES_RCVD Envelope sender domain matches handover relay
domain
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/400>
Post by Pascal Costanza
Post by Matthew D. Swank
I have implemented a small fexpr interpreter in Common Lisp based on
Kernel http://web.cs.wpi.edu/~jshutt/kernel.html. Right now it's a Lisp
1, but I am considering trying to make it a more idiomatic extension of
Common Lisp by making it a Lisp 2.
Part of the Lisp 2-ness of the Common Lisp evaluator is that the car of
a form must name a function, macro, or special form. This name is either
a symbol bound in the function name space, or a lambda expression.
However, Kernel just requires the car evaluate to a combiner (this is
what Kernel calls a generic operator). Obviously, in a Lisp 2, a symbol
would evaluate to the value bound to it in the function name space.
((returns-a-function) arg arg ...)
Would it be reasonable to allow this as a legal form as well?
I'm not arguing Common Lisp should work this way, but I seems to make
sense in the context of a Kernel like evaluator.
_If_ (returns-a-function) indeed returns a function, then this could be
ok. But what if it doesn't return a function? What if it is a macro that
returns just a symbol? Do you want to risk that ((return-something) ...) has
a different meaning than (funcall (return-something) ...)? This is
potentially confusing and could lead to code that is hard to debug...
Maybe no harder than other Lisp-2's :-)

It seems like an interesting extension of the term "Lisp-2" -- as well as just
specifying different namespaces, the proposal is to have a different evaluator
for the car of the form. In fact, CL already has one, but it is very limited.

If that evaluator allows macro forms, then a macro that expands to a symbol
should work as if the symbol was used directly. If you use such a macro with
(funcall (return-something) ...), then you are using the regular evaluator for
the macro form.
--
Martin Simmons
LispWorks Ltd
http://www.lispworks.com/
Raffael Cavallaro
2011-05-25 13:16:26 UTC
Permalink
Content preview: On May 25, 2011, at 7:45 AM, Martin Simmons wrote: > It seems
like an interesting extension of the term "Lisp-2" -- as well as just > specifying
different namespaces, the proposal is to have a different evaluator > for
the car of the form. In fact, CL already has one, but it is very limited.
[...]

Content analysis details: (0.0 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
0.0 FREEMAIL_FROM Sender email is freemail (raffaelcavallaro[at]mac.com)
-0.0 RCVD_IN_DNSWL_NONE RBL: Sender listed at http://www.dnswl.org/, low
trust
[17.148.16.94 listed in list.dnswl.org]
-0.0 T_RP_MATCHES_RCVD Envelope sender domain matches handover relay
domain
-0.0 SPF_PASS SPF: sender matches SPF record
0.0 T_TO_NO_BRKTS_FREEMAIL T_TO_NO_BRKTS_FREEMAIL
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/401>
Post by Martin Simmons
It seems like an interesting extension of the term "Lisp-2" -- as well as just
specifying different namespaces, the proposal is to have a different evaluator
for the car of the form. In fact, CL already has one, but it is very limited.
If I'm not mistaken, this extension has already been implemented for ccl by Ron Garret:

<http://www.flownet.com/ron/lisp/combination-hook.lisp>

warmest regards,

Ralph


Raffael Cavallaro
raffaelcavallaro-BUHhN+***@public.gmane.org
Matthew D. Swank
2011-05-25 23:34:44 UTC
Permalink
Content preview: On 05/25/2011 06:45 AM, Martin Simmons wrote: > It seems like
an interesting extension of the term "Lisp-2" -- as well as just > specifying
different namespaces, the proposal is to have a different evaluator > for
the car of the form. In fact, CL already has one, but it is very limited.
Post by Martin Simmons
[...]
Content analysis details: (-0.0 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
-0.0 RCVD_IN_DNSWL_NONE RBL: Sender listed at http://www.dnswl.org/, low
trust
[209.225.8.23 listed in list.dnswl.org]
-0.0 T_RP_MATCHES_RCVD Envelope sender domain matches handover relay
domain
-0.0 SPF_PASS SPF: sender matches SPF record
0.0 RFC_ABUSE_POST Both abuse and postmaster missing on sender domain
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/408>
Post by Martin Simmons
It seems like an interesting extension of the term "Lisp-2" -- as well as just
specifying different namespaces, the proposal is to have a different evaluator
for the car of the form. In fact, CL already has one, but it is very limited.
If that evaluator allows macro forms, then a macro that expands to a symbol
should work as if the symbol was used directly. If you use such a macro with
(funcall (return-something) ...), then you are using the regular evaluator for
the macro form.
Well, the concrete interpreter I am working on uses a form of fexprs as
the fundamental operators in the language. There wouldn't be macro
'phase' as such to consider. For ((returns-something) arg ...) to work like
(funcall (returns-something) arg ...) the evaluator, in addition to
evaluating compound expressions that occur in the car of a form, would
need to coerce those expressions that evaluate to symbols.

In a purely Common Lisp context, if the expression in the car is "macros
all the way down", you could make a case that form as a whole should be
evaluated in a macro context. That would be interesting to debug as well.

Matt
Matthew Swank
2011-05-25 14:45:39 UTC
Permalink
Content preview: Pascal Costanza <***@...> writes: > > > On 25 May 2011, at
04:51, Matthew D. Swank wrote: > > However, consider the following: > > >
((returns-a-function) arg arg ...) > > > > Would it be reasonable to allow
this as a legal form as well? > > > > I'm not arguing Common Lisp should
work this way, but I seems to make > > sense in the context of a Kernel like
evaluator. > > _If_ (returns-a-function) indeed returns a function, then
this could be ok. > But what if it doesn't return a function? What if it is
a macro that > returns just a symbol? Do you want to risk that ((return-something)
...) has a different meaning than (funcall (return-something) ...)? > This
is potentially confusing and could lead to code that is > hard to debug...
[...]
Content analysis details: (-2.3 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
0.0 FREEMAIL_FROM Sender email is freemail
(akopa.gmane.poster[at]gmail.com)
-2.3 RCVD_IN_DNSWL_MED RBL: Sender listed at http://www.dnswl.org/, medium
trust
[80.91.229.12 listed in list.dnswl.org]
-0.0 SPF_HELO_PASS SPF: HELO matches SPF record
-0.0 T_RP_MATCHES_RCVD Envelope sender domain matches handover relay
domain
-0.0 SPF_PASS SPF: sender matches SPF record
0.0 T_TO_NO_BRKTS_FREEMAIL T_TO_NO_BRKTS_FREEMAIL
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/402>
Post by Matthew D. Swank
((returns-a-function) arg arg ...)
Would it be reasonable to allow this as a legal form as well?
I'm not arguing Common Lisp should work this way, but I seems to make
sense in the context of a Kernel like evaluator.
_If_ (returns-a-function) indeed returns a function, then this could be ok.
But what if it doesn't return a function? What if it is a macro that
returns just a symbol? Do you want to risk that ((return-something)
...) has a different meaning than (funcall (return-something) ...)?
This is potentially confusing and could lead to code that is
hard to debug...
Yes you'd have to watch for symbols. The idiom would be to coerce values for use
in the car:

((callable (returns-a-function?)) arg arg ...)

or stick to using funcall.

Matt
Alessio Stalla
2011-05-25 15:15:34 UTC
Permalink
Content preview: On Wed, May 25, 2011 at 4:45 PM, Matthew Swank wrote: > Pascal
Costanza <***@...> writes: > >> >> >> On 25 May 2011, at 04:51, Matthew D.
Swank wrote: > >> > However, consider the following: >> > >> > ((returns-a-function)
arg arg ...) >> > >> > Would it be reasonable to allow this as a legal form
as well? >> > >> > I'm not arguing Common Lisp should work this way, but
I seems to make >> > sense in the context of a Kernel like evaluator. >> >>
_If_ (returns-a-function) indeed returns a function, then this could be ok.
Post by Matthew Swank
But what if it doesn't return a function? What if it is a macro that >>
returns just a symbol? Do you want to risk that ((return-something) >> ...)
has a different meaning than (funcall (return-something) ...)? >> This is
potentially confusing and could lead to code that is >> hard to debug...
Post by Matthew Swank
Post by Matthew D. Swank
Post by Matthew Swank
Yes you'd have to watch for symbols. The idiom would be to coerce values
for use > in the car: > > ((callable (returns-a-function?)) arg arg ...)
Post by Matthew Swank
or stick to using funcall. [...]
Content analysis details: (-100.7 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
-0.7 RCVD_IN_DNSWL_LOW RBL: Sender listed at http://www.dnswl.org/, low
trust
[209.85.216.51 listed in list.dnswl.org]
-100 USER_IN_WHITELIST From: address is in the user's white-list
0.0 FREEMAIL_FROM Sender email is freemail (alessiostalla[at]gmail.com)
-0.0 SPF_PASS SPF: sender matches SPF record
0.0 RFC_ABUSE_POST Both abuse and postmaster missing on sender domain
0.0 T_DKIM_INVALID DKIM-Signature header exists but is not valid
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/403>

On Wed, May 25, 2011 at 4:45 PM, Matthew Swank
Post by Matthew Swank
Post by Matthew D. Swank
((returns-a-function) arg arg ...)
Would it be reasonable to allow this as a legal form as well?
I'm not arguing Common Lisp should work this way, but I seems to make
sense in the context of a Kernel like evaluator.
_If_ (returns-a-function) indeed returns a function, then this could be ok.
But what if it doesn't return a function? What if it is a macro that
returns just a symbol? Do you want to risk that ((return-something)
...) has a different meaning than (funcall (return-something) ...)?
This is  potentially confusing and could lead to code that is
hard to debug...
Yes you'd have to watch for symbols. The idiom would be to coerce values for use
((callable (returns-a-function?)) arg arg ...)
or stick to using funcall.
While in principle I like such a thing, I think it doesn't play well
with Lisp-2 (or more specifically, with Common Lisp). If ((whatever)
...) is a valid expression, then one would expect (let ((foo
(whatever))) (foo ...)) to be equivalent, but it's not. And you can't
use flet/labels for the same effect. Perhaps this is an oversight in
flet: if it were a little more verbose - (flet ((x (lambda ...))) ...)
- then you could also admit a more general form (flet ((x
(returns-a-function))) ...). It would also be more symmetric with let.
Of course, in general, the compiler would only optimize the former
case, where the function is statically known. Hmm... this should go in
my "CL++" wish list :D

Alessio
Matthew Swank
2011-05-25 15:51:28 UTC
Permalink
Content preview: Alessio Stalla <***@...> writes: > > On Wed, May
25, 2011 at 4:45 PM, Matthew Swank > <***@...> wrote: > >
Pascal Costanza <***@...> writes: > > > >> > >> > >> On 25 May 2011, at 04:51,
Matthew D. Swank wrote: > > > >> > However, consider the following: > >>
Post by Alessio Stalla
Post by Matthew D. Swank
((returns-a-function) arg arg ...) > >> > > >> > Would it be reasonable
to allow this as a legal form as well? > > While in principle I like such
a thing, I think it doesn't play well > with Lisp-2 (or more specifically,
with Common Lisp). If ((whatever) > ...) is a valid expression, then one
would expect (let ((foo > (whatever))) (foo ...)) to be equivalent, but it's
not. And you can't > use flet/labels for the same effect. [...]

Content analysis details: (-2.3 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
0.0 FREEMAIL_FROM Sender email is freemail
(akopa.gmane.poster[at]gmail.com)
-2.3 RCVD_IN_DNSWL_MED RBL: Sender listed at http://www.dnswl.org/, medium
trust
[80.91.229.12 listed in list.dnswl.org]
-0.0 SPF_HELO_PASS SPF: HELO matches SPF record
-0.0 T_RP_MATCHES_RCVD Envelope sender domain matches handover relay
domain
-0.0 SPF_PASS SPF: sender matches SPF record
0.0 T_TO_NO_BRKTS_FREEMAIL T_TO_NO_BRKTS_FREEMAIL
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/404>
Post by Alessio Stalla
On Wed, May 25, 2011 at 4:45 PM, Matthew Swank
Post by Matthew D. Swank
((returns-a-function) arg arg ...)
Would it be reasonable to allow this as a legal form as well?
While in principle I like such a thing, I think it doesn't play well
with Lisp-2 (or more specifically, with Common Lisp). If ((whatever)
...) is a valid expression, then one would expect (let ((foo
(whatever))) (foo ...)) to be equivalent, but it's not. And you can't
use flet/labels for the same effect.
Well, let bindings could be extended to use an operator to specify the namespace:

(let (((function foo) (lambda (arg ...) ...))
(bar (lambda (arg ...) ...)))
(foo ...)
(funcall bar ...))


and flet/labels would transform into a generalized let binding.

This would make the standard transformation of let -> function call a little
problematic, however.

I suppose at the bottom of all this is an implied primitive binding operator for
operators: perhaps flambda!

Matt
Marco Antoniotti
2011-05-25 19:40:35 UTC
Permalink
Hi

I don't think there is a reasonable objection to forbid a form like

((returns-something-funcallable arg1 arg2 ... argN) 1 2 3 ... N)

from "working as expected". As Martin pointed out, if the return value of the form is a "macro" then this would have to be interpreted in the "regular" evaluation regime.

As per "extending" LET there have been a lot of proposals... IMHO a nice one is to go the LOOP way :)

(LETS [var <symbol> <form>]*
[fun (<name> <arglist> <body>)]*
[labels (<name> <arglist> <body>)]*
[values <list> <form>]*
IN
<body>)

Of course you can add some ways of extending the syntax by having something like

(def-lets-binding <tag> ...)

You get the idea....

Cheers
--
MA
Post by Matthew Swank
Post by Alessio Stalla
On Wed, May 25, 2011 at 4:45 PM, Matthew Swank
Post by Matthew D. Swank
((returns-a-function) arg arg ...)
Would it be reasonable to allow this as a legal form as well?
While in principle I like such a thing, I think it doesn't play well
with Lisp-2 (or more specifically, with Common Lisp). If ((whatever)
...) is a valid expression, then one would expect (let ((foo
(whatever))) (foo ...)) to be equivalent, but it's not. And you can't
use flet/labels for the same effect.
(let (((function foo) (lambda (arg ...) ...))
(bar (lambda (arg ...) ...)))
(foo ...)
(funcall bar ...))
and flet/labels would transform into a generalized let binding.
This would make the standard transformation of let -> function call a little
problematic, however.
I suppose at the bottom of all this is an implied primitive binding operator for
operators: perhaps flambda!
Matt
_______________________________________________
pro mailing list
http://lists.common-lisp.net/cgi-bin/mailman/listinfo/pro
--
Marco Antoniotti, Associate Professor tel. +39 - 02 64 48 79 01
DISCo, Università Milano Bicocca U14 2043 http://bimib.disco.unimib.it
Viale Sarca 336
I-20126 Milan (MI) ITALY

Please note that I am not checking my Spam-box anymore.
Please do not forward this email without asking me first.
Alessio Stalla
2011-05-25 21:05:51 UTC
Permalink
Content preview: On Wed, May 25, 2011 at 9:40 PM, Marco Antoniotti wrote: >
Hi > I don't think there is a reasonable objection to forbid a form like
((returns-something-funcallable arg1 arg2 ... argN) 1 2 3 ... N) > from
"working as expected". [...]

Content analysis details: (-100.7 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
-100 USER_IN_WHITELIST From: address is in the user's white-list
0.0 FREEMAIL_FROM Sender email is freemail (alessiostalla[at]gmail.com)
-0.7 RCVD_IN_DNSWL_LOW RBL: Sender listed at http://www.dnswl.org/, low
trust
[209.85.216.179 listed in list.dnswl.org]
-0.0 SPF_PASS SPF: sender matches SPF record
0.0 RFC_ABUSE_POST Both abuse and postmaster missing on sender domain
0.0 T_DKIM_INVALID DKIM-Signature header exists but is not valid
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/407>

On Wed, May 25, 2011 at 9:40 PM, Marco Antoniotti
Hi
I don't think there is a reasonable objection to forbid a form like
((returns-something-funcallable arg1 arg2 ... argN) 1 2 3 ... N)
from "working as expected".
Me neither ;)
As Martin pointed out, if the return value of
the form is a "macro" then this would have to be interpreted in the
"regular" evaluation regime.
As per "extending" LET there have been a lot of proposals... IMHO a nice one
is to go the LOOP way :)
(LETS [var <symbol> <form>]*
      [fun (<name> <arglist> <body>)]*
      [labels (<name> <arglist> <body>)]*
      [values <list> <form>]*
  IN
  <body>)
Of course you can add some ways of extending the syntax by having something like
(def-lets-binding <tag> ...)
You get the idea....
It's not about syntax, it's about a missing feature: the ability to
bind a symbol's function "cell" to a value that's not known at compile
time. To me, that's a limitation of the spec; given that we have
funcall, it's obviously easy to implement and would be symmetrical to
let. With such a feature, the gap between Lisp-1 and Lisp-2 would be
effectively reduced:

(let ((list 42))
(flet ((list (compose #'nreverse #'list)))
(list #'list list)))

=> (42 #<compiled-function (lambda (...) ...)>)

The code above is horrible, but you get the idea.

Alessio
Matthew D. Swank
2011-05-26 00:07:22 UTC
Permalink
Content preview: On 05/25/2011 04:05 PM, Alessio Stalla wrote: > It's not about
syntax, it's about a missing feature: the ability to > bind a symbol's function
"cell" to a value that's not known at compile > time. I've used this for
pedagogical purposes: (defmacro f-let ((&rest bindings) &body body) (let*
((let-bindings (mapcar (lambda (binding) (list (gensym) (cadr binding))) bindings))
(flet-bindings (mapcar (lambda (binding let-binding) `(,(car binding) (&rest
args) (apply ,(car let-binding) args))) bindings let-bindings))) `(let ,let-bindings
(flet ,flet-bindings ,@body)))) [...]

Content analysis details: (-0.0 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
-0.0 RCVD_IN_DNSWL_NONE RBL: Sender listed at http://www.dnswl.org/, low
trust
[216.33.127.81 listed in list.dnswl.org]
-0.0 T_RP_MATCHES_RCVD Envelope sender domain matches handover relay
domain
-0.0 SPF_PASS SPF: sender matches SPF record
0.0 RFC_ABUSE_POST Both abuse and postmaster missing on sender domain
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/409>
Post by Alessio Stalla
It's not about syntax, it's about a missing feature: the ability to
bind a symbol's function "cell" to a value that's not known at compile
time.
I've used this for pedagogical purposes:
(defmacro f-let ((&rest bindings) &body body)
(let* ((let-bindings (mapcar (lambda (binding)
(list (gensym) (cadr binding)))
bindings))
(flet-bindings (mapcar (lambda (binding let-binding)
`(,(car binding) (&rest args)
(apply ,(car let-binding) args)))
bindings
let-bindings)))
`(let ,let-bindings
(flet ,flet-bindings
,@body))))

but it hardly solves the problem.
Pascal Costanza
2011-05-26 16:35:09 UTC
Permalink
Content preview: On 26 May 2011, at 02:07, Matthew D. Swank wrote: > On 05/25/2011
04:05 PM, Alessio Stalla wrote: >> It's not about syntax, it's about a missing
feature: the ability to >> bind a symbol's function "cell" to a value that's
(defmacro f-let ((&rest bindings) &body body) > (let* ((let-bindings (mapcar
(lambda (binding) > (list (gensym) (cadr binding))) > bindings)) > (flet-bindings
(mapcar (lambda (binding let-binding) > `(,(car binding) (&rest args) > (apply
,(car let-binding) args))) > bindings > let-bindings))) > `(let ,let-bindings
[...]

Content analysis details: (-102.3 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
-100 USER_IN_WHITELIST From: address is in the user's white-list
-2.3 RCVD_IN_DNSWL_MED RBL: Sender listed at http://www.dnswl.org/, medium
trust
[134.184.129.112 listed in list.dnswl.org]
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/412>
Post by Alessio Stalla
It's not about syntax, it's about a missing feature: the ability to
bind a symbol's function "cell" to a value that's not known at compile
time.
(defmacro f-let ((&rest bindings) &body body)
(let* ((let-bindings (mapcar (lambda (binding)
(list (gensym) (cadr binding)))
bindings))
(flet-bindings (mapcar (lambda (binding let-binding)
`(,(car binding) (&rest args)
(apply ,(car let-binding) args)))
bindings
let-bindings)))
`(let ,let-bindings
(flet ,flet-bindings
but it hardly solves the problem.
Why does it not solve the problem? Your definition shows that adding such a feature is just a matter of defining a macro, so it's more or less at the same level of adding a looping construct - it doesn't increase the expressiveness of the language (in the sense of Felleisen's macro-expressiveness).

So, what "problem" do you have in mind here?


Pascal

--
Pascal Costanza
The views expressed in this email are my own, and not those of my employer.
Marco Antoniotti
2011-05-26 09:34:41 UTC
Permalink
Content preview: On May 25, 2011, at 23:05 , Alessio Stalla wrote: > On Wed,
May 25, 2011 at 9:40 PM, Marco Antoniotti > <antoniotti.marco-***@public.gmane.org>
wrote: >> Hi >> I don't think there is a reasonable objection to forbid a
form like >> ((returns-something-funcallable arg1 arg2 ... argN) 1 2 3 ...
N) >> from "working as expected". > > Me neither ;) > >> As Martin pointed
out, if the return value of >> the form is a "macro" then this would have
to be interpreted in the >> "regular" evaluation regime. >> As per "extending"
LET there have been a lot of proposals... IMHO a nice one >> is to go the
LOOP way :) >> (LETS [var <symbol> <form>]* >> [fun (<name> <arglist> <body>)]*
Post by Alessio Stalla
[labels (<name> <arglist> <body>)]* >> [values <list> <form>]* >> IN >>
<body>) >> Of course you can add some ways of extending the syntax by having
something >> like >> (def-lets-binding <tag> ...) >> You get the idea....
Post by Alessio Stalla
It's not about syntax, it's about a missing feature: the ability to >
bind a symbol's function "cell" to a value that's not known at compile >
time. To me, that's a limitation of the spec; given that we have > funcall,
it's obviously easy to implement and would be symmetrical to > let. With
Post by Alessio Stalla
(let ((list 42)) > (flet ((list (compose #'nreverse #'list))) > (list
#'list list))) > > => (42 #<compiled-function (lambda (...) ...)>) > > The
code above is horrible, but you get the idea. [...]

Content analysis details: (-0.0 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
0.0 SINGLE_HEADER_2K A single header contains 2K-3K characters
-0.0 T_RP_MATCHES_RCVD Envelope sender domain matches handover relay
domain
-0.0 SPF_PASS SPF: sender matches SPF record
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/410>
Post by Alessio Stalla
On Wed, May 25, 2011 at 9:40 PM, Marco Antoniotti
Hi
I don't think there is a reasonable objection to forbid a form like
((returns-something-funcallable arg1 arg2 ... argN) 1 2 3 ... N)
from "working as expected".
Me neither ;)
As Martin pointed out, if the return value of
the form is a "macro" then this would have to be interpreted in the
"regular" evaluation regime.
As per "extending" LET there have been a lot of proposals... IMHO a nice one
is to go the LOOP way :)
(LETS [var <symbol> <form>]*
[fun (<name> <arglist> <body>)]*
[labels (<name> <arglist> <body>)]*
[values <list> <form>]*
IN
<body>)
Of course you can add some ways of extending the syntax by having something like
(def-lets-binding <tag> ...)
You get the idea....
It's not about syntax, it's about a missing feature: the ability to
bind a symbol's function "cell" to a value that's not known at compile
time. To me, that's a limitation of the spec; given that we have
funcall, it's obviously easy to implement and would be symmetrical to
let. With such a feature, the gap between Lisp-1 and Lisp-2 would be
(let ((list 42))
(flet ((list (compose #'nreverse #'list)))
(list #'list list)))
=> (42 #<compiled-function (lambda (...) ...)>)
The code above is horrible, but you get the idea.
Yep. This has been discussed before (*)... If I remember correctly you can get almost there by specifying differently what you are doing when dealing with the OP of a form, when this is a symbol. My recollection is that it is doable and that the rationale for not allowing it is mostly to make compiler writing easier (although I think that that should be a piece of cake today).

The problem is that you have to prioritize the namespace you are searching, thus ushering in a more complex set of rules for the programmer to remember. IMHO, this is not a very good reason to "leave it out" since it has been proved over and over again that languages which increase a programmer's self esteem are also those with the absolutely most convoluted access rules ever :) Plus these languages are also very successful :)

Cheers
--
Marco



(*) It's in CLL.


--
Marco Antoniotti, Associate Professor tel. +39 - 02 64 48 79 01
DISCo, Università Milano Bicocca U14 2043 http://bimib.disco.unimib.it
Viale Sarca 336
I-20126 Milan (MI) ITALY

Please note that I am not checking my Spam-box anymore.
Please do not forward this email without asking me first.
Pascal Costanza
2011-05-26 16:32:56 UTC
Permalink
Post by Marco Antoniotti
Hi
I don't think there is a reasonable objection to forbid a form like
((returns-something-funcallable arg1 arg2 ... argN) 1 2 3 ... N)
from "working as expected". As Martin pointed out, if the return value of the form is a "macro" then this would have to be interpreted in the "regular" evaluation regime.
The main issue I have with this is that at the moment, you have only explicit shifting operators (funcall/apply and function/symbol-function/fdefinition). A proposal like the one above would introduce implicit shifting.

You already have implicit shifting in the sense that placing a symbol in the car or any of the cdr positions is already enough to fetch something from the function or the value namespace. However, you can only do this with explicit function/variable names directly in the "user" code, or by constructing the correct s-expressions in macro definitions. With a proposal like the above, you would add another level of implicit shifting.

If I define a function, say (defun foo () 'bar), and a corresponding macro (defmacro foom () (foo)), then without explicit shifting and without macros, I can only use this to generate a variable name (baz (foom)), but not to generate a function name, because ((foom) baz) fails. With the proposal above, ((foom) baz) wouldn't fail. I prefer the explicitness of (funcall (foom) baz), especially because if you really, really, really want it implicit, you can still have it your way anyway.


Pascal

--
Pascal Costanza
The views expressed in this email are my own, and not those of my employer.
Marco Antoniotti
2011-06-04 10:34:50 UTC
Permalink
Post by Pascal Costanza
Post by Marco Antoniotti
Hi
I don't think there is a reasonable objection to forbid a form like
((returns-something-funcallable arg1 arg2 ... argN) 1 2 3 ... N)
from "working as expected". As Martin pointed out, if the return value of the form is a "macro" then this would have to be interpreted in the "regular" evaluation regime.
The main issue I have with this is that at the moment, you have only explicit shifting operators (funcall/apply and function/symbol-function/fdefinition). A proposal like the one above would introduce implicit shifting.
You already have implicit shifting in the sense that placing a symbol in the car or any of the cdr positions is already enough to fetch something from the function or the value namespace. However, you can only do this with explicit function/variable names directly in the "user" code, or by constructing the correct s-expressions in macro definitions. With a proposal like the above, you would add another level of implicit shifting.
If I define a function, say (defun foo () 'bar), and a corresponding macro (defmacro foom () (foo)), then without explicit shifting and without macros, I can only use this to generate a variable name (baz (foom)), but not to generate a function name, because ((foom) baz) fails. With the proposal above, ((foom) baz) wouldn't fail. I prefer the explicitness of (funcall (foom) baz), especially because if you really, really, really want it implicit, you can still have it your way anyway.
I think this are good reasons, but not enough to disallow the following:

(<symbol or form-returning-a-function-not-a-symbol or lambda-expression> ...)

We already have

((lambda (x) (+ x 42)) 0)

Why not have

((compose 'first 'rest) '(1 2 3))

This would complicate the call protocol and require more explanation, but I really don't see how it would harm the programmer.

Cheers
--
MA
Post by Pascal Costanza
Pascal
--
Pascal Costanza
The views expressed in this email are my own, and not those of my employer.
--
Marco Antoniotti, Associate Professor tel. +39 - 02 64 48 79 01
DISCo, Università Milano Bicocca U14 2043 http://bimib.disco.unimib.it
Viale Sarca 336
I-20126 Milan (MI) ITALY

Please note that I am not checking my Spam-box anymore.
Please do not forward this email without asking me first.
Kazimir Majorinc
2011-06-04 10:06:44 UTC
Permalink
Content preview: On 25.5.2011. 4:51, Matthew D. Swank wrote: > I have implemented
a small fexpr interpreter in Common Lisp based on > Kernel http://web.cs.wpi.edu/~jshutt/kernel.html.
Right now it's a Lisp > 1, but I am considering trying to make it a more
idiomatic extension of > Common Lisp by making it a Lisp 2. [...]

Content analysis details: (0.7 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
-0.0 RCVD_IN_DNSWL_NONE RBL: Sender listed at http://www.dnswl.org/, low
trust
[195.29.150.135 listed in list.dnswl.org]
0.7 SPF_NEUTRAL SPF: sender does not match SPF record (neutral)
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/414>
Post by Matthew D. Swank
I have implemented a small fexpr interpreter in Common Lisp based on
Kernel http://web.cs.wpi.edu/~jshutt/kernel.html. Right now it's a Lisp
1, but I am considering trying to make it a more idiomatic extension of
Common Lisp by making it a Lisp 2.
Did you published anything online?

How would you estimate time / space requirements compared to original
dynamically scoped FEXPRs?
Matthew D. Swank
2011-06-04 13:43:47 UTC
Permalink
Content preview: On 06/04/2011 05:06 AM, Kazimir Majorinc wrote: > On 25.5.2011.
4:51, Matthew D. Swank wrote: > >> I have implemented a small fexpr interpreter
in Common Lisp based on >> Kernel http://web.cs.wpi.edu/~jshutt/kernel.html.
Right now it's a Lisp >> 1, but I am considering trying to make it a more
idiomatic extension of >> Common Lisp by making it a Lisp 2. > > Did you
published anything online? > Not yet. I'm still making my way though the two
relevant papers to see what can be adapted. My interpreter sticks pretty
close to the exposition of vau-expressions in the first half of Dr Shutt's
dissertation. > How would you estimate time / space requirements compared
to original > dynamically scoped FEXPRs? > I can't speak intelligently about
that, except to note the overhead that statically scoped lisps have generally.
[...]

Content analysis details: (-0.0 points, 5.0 required)

pts rule name description
---- ---------------------- --------------------------------------------------
-0.0 RCVD_IN_DNSWL_NONE RBL: Sender listed at http://www.dnswl.org/, low
trust
[216.33.127.81 listed in list.dnswl.org]
-0.0 T_RP_MATCHES_RCVD Envelope sender domain matches handover relay
domain
-0.0 SPF_PASS SPF: sender matches SPF record
0.0 RFC_ABUSE_POST Both abuse and postmaster missing on sender domain
Archived-At: <http://permalink.gmane.org/gmane.lisp.cl-pro/416>
Post by Kazimir Majorinc
Post by Matthew D. Swank
I have implemented a small fexpr interpreter in Common Lisp based on
Kernel http://web.cs.wpi.edu/~jshutt/kernel.html. Right now it's a Lisp
1, but I am considering trying to make it a more idiomatic extension of
Common Lisp by making it a Lisp 2.
Did you published anything online?
Not yet. I'm still making my way though the two relevant papers to see
what can be adapted. My interpreter sticks pretty close to the
exposition of vau-expressions in the first half of Dr Shutt's dissertation.
Post by Kazimir Majorinc
How would you estimate time / space requirements compared to original
dynamically scoped FEXPRs?
I can't speak intelligently about that, except to note the overhead that
statically scoped lisps have generally.

Matt

Continue reading on narkive:
Loading...