
binding multiple values (Ex: Re: some small proposed changes to standard)
Quote:
> | Although there are other reasons why
> |
> | (let (((the integer i) ...)) ...)
> |
> | would be simplest.
> the symmetry with how it would be written in the absence of declarations
> is appealing, but although I favored this form myself previously, they
> "bury" the variables that are being bound in a lot of clutter, making it
> hard to locate what is being bound. if your reasoning above is valid, it
> appears to be more cause for concern for typos and problems with this
> approach than the one above.
We talked about this long ago
in the destructuring discussion. The key reason to have
(letbind (((values x y) (values 3 4)) ..))
instead of
(letbind (((x y) (values 3 4))) ...)
is to allow things other than VALUES to be used. e.g., constructors.
And once you allow
(letbind (((cons a b) (cons 3 4))) ...)
then you might also want abstractions like
(letbind (((make-instance 'foo :a 3 :b 4) (current-foo))) ...)
and you might want that to be implemented by macroexpansion so that
(macrolet ((xcons (x y) `(cons ,x ,y)))
(letbind (((xcons a b) (cons 1 2))) ...))
==>
(letbind (((cons b a) (cons 1 2))) ...)
==>
(let ((b 1) (a 2)) ...)
And if that can be the case, then you might want just
(macrolet ((ivalue (x) `(the integer ,x)))
(letbind (((ivalue z) 3)) ...))
or
(macrolet ((sizes (x y) `(the (values integer integer) (values ,x ,y))))
(letbind (((sizes width height) (window-size foo)))
...))
So burying the type in the part to bind might be useful if the purpose
is to let it ride around invisibly.
I do agree with you the macroexpanded part is cumbersome,
but then so is a LET macroexpanded into a LAMBDA.
Sometimes you put things in the language just to support
nice composition, and I was thinking this might be a good such place.
Before anyone flags me on the issue of macroexpanding here, though,
let me be sure to do some disclaiming right up front:
I admit it's a little weird to say that LET might macroexpand in a
context where the variables are imminently-to-be-bound. That is, in:
(defmacro foo (x) `(the float ,x))
(let ((a 3))
(declare (fixnum a))
(letbind (((foo a) z)) ...))
where A while FOO is playing with it is{*filter*} delicately perched between
two universes. I can't see a "screw case" to this, but I smell one close by.