Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Default argument values for blocks

25 views
Skip to first unread message

Daniel Schierbeck

unread,
Oct 11, 2005, 12:52:04 PM10/11/05
to
Is there a reason why I can't do this?

foo = lambda { |foo = bar| puts foo }
foo.call

I can't think of any good reason why this isn't valid.


Cheers,
Daniel Schierbeck

Daniel Schierbeck

unread,
Oct 11, 2005, 1:01:24 PM10/11/05
to

I of course meant |foo = "bar"|

Sorry

Yukihiro Matsumoto

unread,
Oct 11, 2005, 1:25:33 PM10/11/05
to
Hi,

In message "Re: Default argument values for blocks"


on Wed, 12 Oct 2005 01:56:52 +0900, Daniel Schierbeck <daniel.s...@gmail.com> writes:

|Is there a reason why I can't do this?
|
| foo = lambda { |foo = bar| puts foo }
| foo.call
|
|I can't think of any good reason why this isn't valid.

Mostly because yacc does not allow it. It confuses

lambda { |foo = bar| puts foo }

as

lambda { |foo = (bar| puts foo) }

and causes syntax error.

matz.


Yukihiro Matsumoto

unread,
Oct 11, 2005, 1:29:35 PM10/11/05
to
Hi,

In message "Re: Default argument values for blocks"

on Wed, 12 Oct 2005 02:25:33 +0900, Yukihiro Matsumoto <ma...@ruby-lang.org> writes:

||Is there a reason why I can't do this?
||
|| foo = lambda { |foo = bar| puts foo }
|| foo.call
||
||I can't think of any good reason why this isn't valid.
|
|Mostly because yacc does not allow it. It confuses
|
| lambda { |foo = bar| puts foo }
|
|as
|
| lambda { |foo = (bar| puts foo) }
|
|and causes syntax error.

For your information, you can do

foo = ->(foo="bar"){puts foo}
foo.call

in 1.9.

matz.


Ara.T.Howard

unread,
Oct 11, 2005, 1:40:48 PM10/11/05
to

-> means lambda?

-a
--
===============================================================================
| email :: ara [dot] t [dot] howard [at] noaa [dot] gov
| phone :: 303.497.6469
| Your life dwells amoung the causes of death
| Like a lamp standing in a strong breeze. --Nagarjuna
===============================================================================

Daniel Schierbeck

unread,
Oct 11, 2005, 2:12:15 PM10/11/05
to

Cool. Is "->" the same as "lambda"? Can you write this:

collection.each -> (element) { puts element }

Kevin Ballard

unread,
Oct 11, 2005, 3:18:25 PM10/11/05
to
Yukihiro Matsumoto wrote:
> Mostly because yacc does not allow it. It confuses
>
> lambda { |foo = bar| puts foo }
>
> as
>
> lambda { |foo = (bar| puts foo) }
>
> and causes syntax error.

yacc? Maybe I was informed wrong, but I was under the impression that
Ruby used a hand-rolled parser.

Daniel Berger

unread,
Oct 11, 2005, 3:24:00 PM10/11/05
to

MY EYES!!!!

Please, no.

Dan


Eric Hodel

unread,
Oct 11, 2005, 5:08:15 PM10/11/05
to
On Oct 11, 2005, at 12:21 PM, Kevin Ballard wrote:

> Yukihiro Matsumoto wrote:
>> Mostly because yacc does not allow it.
>

> yacc? Maybe I was informed wrong, but I was under the impression that
> Ruby used a hand-rolled parser.

You were informed wrong.

itsme213

unread,
Oct 11, 2005, 5:40:02 PM10/11/05
to

"Yukihiro Matsumoto" <ma...@ruby-lang.org> wrote in message

> For your information, you can do
>
> foo = ->(foo="bar"){puts foo}

I hope you can find a better syntax ...


David A. Black

unread,
Oct 11, 2005, 5:40:07 PM10/11/05
to
Hi --

On Wed, 12 Oct 2005, Yukihiro Matsumoto wrote:

Is this definitely going to remain? (Please say no.... :-)


David

--
David A. Black
dbl...@wobblini.net


Berger, Daniel

unread,
Oct 11, 2005, 5:43:28 PM10/11/05
to

> -----Original Message-----
> From: itsme213 [mailto:itsm...@hotmail.com]
> Sent: Tuesday, October 11, 2005 3:42 PM
> To: ruby-talk ML
> Subject: Re: Default argument values for blocks
>
>
>
> "Yukihiro Matsumoto" <ma...@ruby-lang.org> wrote in message
>

> > For your information, you can do
> >
> > foo = ->(foo="bar"){puts foo}
>

> I hope you can find a better syntax ...

Or better yet, just drop the idea of default argument values for blocks
altogether. I still haven't seen what problem this is trying to solve.

Dan


D'Andrew "Dave" Thompson

unread,
Oct 11, 2005, 5:47:27 PM10/11/05
to
unsubscribe

itsme213

unread,
Oct 11, 2005, 7:13:01 PM10/11/05
to

"Berger, Daniel" <Daniel...@qwest.com> wrote in message

> > foo = ->(foo="bar"){puts foo}

> Or better yet, just drop the idea of default argument values for blocks


> altogether. I still haven't seen what problem this is trying to solve.

Please don't do that, some apps need to define methods dynamically (e.g.
with define_method) and blocks let them do this with closures.


Yukihiro Matsumoto

unread,
Oct 11, 2005, 8:04:26 PM10/11/05
to
Hi,

In message "Re: Default argument values for blocks"

on Wed, 12 Oct 2005 02:40:48 +0900, "Ara.T.Howard" <Ara.T....@noaa.gov> writes:

|> foo = ->(foo="bar"){puts foo}

|-> means lambda?

Yes, as in Perl6. "lambda" here means lambda in other languages, not
the lambda method in Ruby.

matz.


Yukihiro Matsumoto

unread,
Oct 11, 2005, 8:06:12 PM10/11/05
to
Hi,

In message "Re: Default argument values for blocks"

on Wed, 12 Oct 2005 06:40:07 +0900, "David A. Black" <dbl...@wobblini.net> writes:

|> foo = ->(foo="bar"){puts foo}

|Is this definitely going to remain? (Please say no.... :-)

It is, but appearance may be changed. But I haven't got the better
one.

matz.


Eric Mahurin

unread,
Oct 11, 2005, 9:01:44 PM10/11/05
to

Other than syntax, what's the difference between this and the
Proc that comes from the lambda method? Maybe how return,
break, etc is handled?

In addition to handling defaults in arguments, I think these
issues need to be addressed in blocks/lambdas:

- all variables in the defining scope of a block/lambda are
prevented from being GCed by the block/lambda (because of the
#binding). This can easily result in a leaky program if not
careful. I discussed several solutions to this in a previous
thread.

- a facility for making variables local (regardless of whether
a variable of the same name exists in the defining scope).
This would also be good to have for a begin-end type block (I'd
like to have it for making inlined macros where I don't want to
worry about what variables are already used). I discussed
several solutions for this in another thread.

Also, I saw some slides for ruby 2 back in 2003 showing that
arguments will always be local to the block and other variables
in the block will be in the same scope as the defining scope.
I think always making arguments local is a good thing, but
never localizing the other variables will be problematic if
another local variable facility is not provided.




__________________________________
Yahoo! Mail - PC Magazine Editors' Choice 2005
http://mail.yahoo.com


David A. Black

unread,
Oct 11, 2005, 9:13:31 PM10/11/05
to
Hi --

On Wed, 12 Oct 2005, Yukihiro Matsumoto wrote:

I definitely think a keyword would be better than -> .

Yukihiro Matsumoto

unread,
Oct 11, 2005, 9:17:30 PM10/11/05
to
Hi,

In message "Re: Default argument values for blocks"

on Wed, 12 Oct 2005 10:01:44 +0900, Eric Mahurin <eric_m...@yahoo.com> writes:

|Other than syntax, what's the difference between this and the
|Proc that comes from the lambda method? Maybe how return,
|break, etc is handled?

They are same, same class, same behavior, except for full argument
syntax of method arguments.

|In addition to handling defaults in arguments, I think these
|issues need to be addressed in blocks/lambdas:
|
|- all variables in the defining scope of a block/lambda are
|prevented from being GCed by the block/lambda (because of the
|#binding). This can easily result in a leaky program if not
|careful. I discussed several solutions to this in a previous
|thread.

I think this issue should _not_ be solved by making new lambda-like
object, but something like making eval a keyword, so that non
referenced local variable can be erased unless eval is called within
the scope.

|- a facility for making variables local (regardless of whether
|a variable of the same name exists in the defining scope).
|This would also be good to have for a begin-end type block (I'd
|like to have it for making inlined macros where I don't want to
|worry about what variables are already used). I discussed
|several solutions for this in another thread.

In 1.9, you can declare block local variables explicitly, by the
syntax:

foo {|a; b, c| ...} # b and c are block local

so that

b=1
5.times{|i;b|
b=5 # modifying in-block "b"
p [i,b]
}
p b # outer "b" remain unchanged

|Also, I saw some slides for ruby 2 back in 2003 showing that
|arguments will always be local to the block and other variables
|in the block will be in the same scope as the defining scope.
|I think always making arguments local is a good thing, but
|never localizing the other variables will be problematic if
|another local variable facility is not provided.

See above.

matz.


Yukihiro Matsumoto

unread,
Oct 11, 2005, 9:19:03 PM10/11/05
to
Hi,

In message "Re: Default argument values for blocks"

on Wed, 12 Oct 2005 10:13:31 +0900, "David A. Black" <dbl...@wobblini.net> writes:

|I definitely think a keyword would be better than -> .

Maybe. Some prefer verbosity to clarity. So what keyword you think
"the best"?

matz.


ES

unread,
Oct 11, 2005, 9:21:15 PM10/11/05
to

What about either

block = lambda(foo = 'bar') { puts foo } # Implicit

or

block = lambda(foo = 'bar') {|foo| puts foo } # Explicit

Or is -> solving an entirely different problem? (If so, would
you mind stating the problem again or pointing me to an earlier
discussion?)

> matz.

E


Ara.T.Howard

unread,
Oct 11, 2005, 9:39:39 PM10/11/05
to
On Wed, 12 Oct 2005, Yukihiro Matsumoto wrote:

by that you mean it is a 'real' method - not a proc object?

i like -> btw. though =>> has a bit more 'weight'.

regards.

Yukihiro Matsumoto

unread,
Oct 11, 2005, 9:56:33 PM10/11/05
to
Hi,

In message "Re: Default argument values for blocks"

on Wed, 12 Oct 2005 10:39:39 +0900, "Ara.T.Howard" <Ara.T....@noaa.gov> writes:

|> |-> means lambda?
|>
|> Yes, as in Perl6. "lambda" here means lambda in other languages, not
|> the lambda method in Ruby.
|
|by that you mean it is a 'real' method - not a proc object?

By that I mean, it is a syntax, which gives you a Proc object.

|i like -> btw. though =>> has a bit more 'weight'.

It depends on your taste.

matz.


Yukihiro Matsumoto

unread,
Oct 11, 2005, 9:57:14 PM10/11/05
to
Hi,

In message "Re: Default argument values for blocks"

on Wed, 12 Oct 2005 03:16:52 +0900, Daniel Schierbeck <daniel.s...@gmail.com> writes:

|Cool. Is "->" the same as "lambda"? Can you write this:
|
| collection.each -> (element) { puts element }

Yes. It is still experimental though.

matz.


David A. Black

unread,
Oct 11, 2005, 10:01:06 PM10/11/05
to
Hi --

On Wed, 12 Oct 2005, Yukihiro Matsumoto wrote:

In this case I think verbosity *is* clarity :-) The -> thing really
has a "line-noise" quality that looks very out of place to me.

I could imagine using the lambda modification posted earlier:

block = lambda(a,b=1) { ... }

for those few times when this would be necessary.

Another idea, since I think at least 99% of this is about
define_method, would be to make some kind of special case treatment
for define_method. But I can't think of a good way to do that.

Eric Mahurin

unread,
Oct 11, 2005, 10:05:13 PM10/11/05
to
--- Yukihiro Matsumoto <ma...@ruby-lang.org> wrote:
> |In addition to handling defaults in arguments, I think these
> |issues need to be addressed in blocks/lambdas:
> |
> |- all variables in the defining scope of a block/lambda are
> |prevented from being GCed by the block/lambda (because of
> the
> |#binding). This can easily result in a leaky program if not
> |careful. I discussed several solutions to this in a
> previous
> |thread.
>
> I think this issue should _not_ be solved by making new
> lambda-like
> object, but something like making eval a keyword, so that non
> referenced local variable can be erased unless eval is called
> within
> the scope.

I agree. In addition to eval within the block (or even a
method that calls eval), you also have the issue that sometimes
people (including me) have wanted to call eval with
Proc#binding and want access to variables outside the block. I
think the majority of the time that is wanted is when the
binding is from the caller, so those variables won't want to be
GCed yet anyways. One of the solutions I gave was to have all
of the variables not directly referenced in the block be weak
references in Proc#binding, so that GC wouldn't be prevented.
GCing those unused variables would delete the weak references
in Proc#binding. I think this solution would maintain the best
compatibility/flexibility and still solve the problem.

> |- a facility for making variables local (regardless of
> whether
> |a variable of the same name exists in the defining scope).
> |This would also be good to have for a begin-end type block
> (I'd
> |like to have it for making inlined macros where I don't want
> to
> |worry about what variables are already used). I discussed
> |several solutions for this in another thread.
>
> In 1.9, you can declare block local variables explicitly, by
> the
> syntax:
>
> foo {|a; b, c| ...} # b and c are block local
>
> so that
>
> b=1
> 5.times{|i;b|
> b=5 # modifying in-block "b"
> p [i,b]
> }
> p b # outer "b" remain unchanged

EXCELLENT!

Would you consider having something like a begin/end block
having this ability too?

b=1
begin(b)
b=5
p b # => 5
end
p b # => 1

Or maybe if "eval" became a keyword like you mentioned above
and it could also take a block, you could do this instead:

b=1
eval {|;b|
b=5
p b # => 5
}
p b # => 1

I'm wanting to avoid the method calls to do this. If eval was
a keyword (or non-redefinable), the above could accomplish it
because it could be in-lined (like begin-end).

> |Also, I saw some slides for ruby 2 back in 2003 showing that
> |arguments will always be local to the block and other
> variables
> |in the block will be in the same scope as the defining
> scope.
> |I think always making arguments local is a good thing, but
> |never localizing the other variables will be problematic if
> |another local variable facility is not provided.
>
> See above.

It doesn't look like arguments are local yet and all variables
inside the block that are not used yet outside are treated
local:

b=1
i=2
5.times { |i;b|
b=5
c=6
p [i,b]
}
p [i,b] # => [4, 1] # i changed, b not
p c # undefined local variable or method

__________________________________________________
Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around
http://mail.yahoo.com


Karl-Heinz Wild

unread,
Oct 12, 2005, 1:26:39 AM10/12/05
to
On 12.10.2005, at 03:17, Yukihiro Matsumoto wrote:

> In 1.9, you can declare block local variables explicitly, by the
> syntax:
>
> foo {|a; b, c| ...} # b and c are block local

and how I whould have to write that c is global?

foo { | a,b, global c | }
foo { | a, b, <c> | }

Please don't misunderstand my suggestion.
I have no idea if it's possible or not,
but it looks pretty to me :)

regards
Karl-Heinz

Trans

unread,
Oct 12, 2005, 2:12:32 AM10/12/05
to

Eric Mahurin wrote:

> I agree. In addition to eval within the block (or even a
> method that calls eval), you also have the issue that sometimes
> people (including me) have wanted to call eval with
> Proc#binding and want access to variables outside the block. I
> think the majority of the time that is wanted is when the
> binding is from the caller, so those variables won't want to be
> GCed yet anyways. One of the solutions I gave was to have all
> of the variables not directly referenced in the block be weak
> references in Proc#binding, so that GC wouldn't be prevented.
> GCing those unused variables would delete the weak references
> in Proc#binding. I think this solution would maintain the best
> compatibility/flexibility and still solve the problem.

This still avoids a solution to closing scope for other uses. For
instance Class.new.

A = Class.new {
class B
def x; 1; end
end
}

class B
def x; 2; 1
end

A::B
(irb):19: warning: toplevel constant B referenced by A::B

There really needs to be a way to close that off.

T.

Christophe Grandsire

unread,
Oct 12, 2005, 2:15:56 AM10/12/05
to
Selon Karl-Heinz Wild <kh....@wicom.li>:

> >
> > foo {|a; b, c| ...} # b and c are block local
>
> and how I whould have to write that c is global?
>
> foo { | a,b, global c | }
> foo { | a, b, <c> | }
>
> Please don't misunderstand my suggestion.
> I have no idea if it's possible or not,
> but it looks pretty to me :)
>

If I understood the discussion correctly, you *don't* have to write anything if
you want c not to be block local. The planned new behaviour of blocks is that
local variables defined in them will be local to the whole scope, not the block
itself only, *unless* you indicate them explicitly through the syntax above. So
there's no need to indicate globality.

And now someone is probably going to come and say I made a complete fool of
myself and didn't understand what is going on ;) (in other words, take this
with a huge AFAIK in front of it).
--
Christophe Grandsire.

http://rainbow.conlang.free.fr

It takes a straight mind to create a twisted conlang.


Karl-Heinz Wild

unread,
Oct 12, 2005, 2:31:23 AM10/12/05
to
On 12.10.2005, at 08:15, Christophe Grandsire wrote:

> Selon Karl-Heinz Wild <kh....@wicom.li>:
>
>>>
>>> foo {|a; b, c| ...} # b and c are block local
>>>
>>
>> and how I whould have to write that c is global?
>>
>> foo { | a,b, global c | }
>> foo { | a, b, <c> | }
>>
>> Please don't misunderstand my suggestion.
>> I have no idea if it's possible or not,
>> but it looks pretty to me :)
>
> If I understood the discussion correctly, you *don't* have to write
> anything if
> you want c not to be block local. The planned new behaviour of
> blocks is that
> local variables defined in them will be local to the whole scope,
> not the block
> itself only, *unless* you indicate them explicitly through the
> syntax above. So
> there's no need to indicate globality.

You are right. I've overseen that. My intention wasn't to change the
planned new behaviour, only thinking about the syntax.

> And now someone is probably going to come and say I made a complete
> fool of
> myself and didn't understand what is going on ;) (in other words,
> take this
> with a huge AFAIK in front of it).

But really, I'm not shy to be what I am.
Maybe - sometime a fool :)

regards
Karl-Heinz

Trans

unread,
Oct 12, 2005, 2:43:02 AM10/12/05
to

Yukihiro Matsumoto wrote:
> Hi,
>
> In message "Re: Default argument values for blocks"
> on Wed, 12 Oct 2005 02:25:33 +0900, Yukihiro Matsumoto <ma...@ruby-lang.org> writes:
>
> ||Is there a reason why I can't do this?
> ||
> || foo = lambda { |foo = bar| puts foo }
> || foo.call
> ||
> ||I can't think of any good reason why this isn't valid.
> |
> |Mostly because yacc does not allow it. It confuses
> |
> | lambda { |foo = bar| puts foo }
> |
> |as
> |
> | lambda { |foo = (bar| puts foo) }
> |
> |and causes syntax error.
>
> For your information, you can do
>
> foo = ->(foo="bar"){puts foo}
> foo.call

What of &?

a.each( &->(foo="bar"){puts foo} ) # Ick.

Can we drop?

a.each( ->(foo="bar"){puts foo} ) # Better.

T.

Christophe Grandsire

unread,
Oct 12, 2005, 2:48:56 AM10/12/05
to
Selon Eric Mahurin <eric_m...@yahoo.com>:

>
> Would you consider having something like a begin/end block
> having this ability too?
>
> b=1
> begin(b)
> b=5
> p b # => 5
> end
> p b # => 1
>

Interesting. This syntax and the meaning of it remind me of METAFONT's way of
declaring scope (I seem to be one of the few people on Earth besides Knuth who
know a bit of METAFONT, and that's too bad because the language has some
interesting features). In METAFONT (which is structured but not oo) scoping and
subroutine definitions are completely separate. In other words you have to scope
explicitly when you want a new scope. You do that through (surprisingly enough
;) ) a "begin... end;" block. In the block, all variables from the outside
scope are known, so if you want to reuse the name of one of those locally you
have to explicitly "save" it first. So in METAFONT your example would read:

b=1;
begin
save b;
b=5;
message b % => 5
end;
message b; % => 1

I must say I like the "save b" syntax. If begin/end blocks in Ruby are to have
the same ability, it may be an idea (I personally find "begin(b)" unclear It
looks more to me like you're starting a block somehow indicated by a kind of
label "b" or something like that ;) ).

Thomas

unread,
Oct 12, 2005, 4:08:15 AM10/12/05
to
> What of &?
>
> a.each( &->(foo="bar"){puts foo} ) # Ick.
>
> Can we drop?
>
> a.each( ->(foo="bar"){puts foo} ) # Better.

I was dreaming for a long time of a ruby dialect that has all these
fancy arrows haskell has. Everybody proposing arrows, please (try to)
read some haskell code.

But seriosly, I personally would prefer something in the line lambda(x,
y=1) {...} as it was proposed by other people too.

The => in the hash syntax is IMHO already one kind of arrow too much.

Regards,
Thomas.


Martin DeMello

unread,
Oct 12, 2005, 7:40:33 AM10/12/05
to
Thomas <sanobas...@yahoo.de> wrote:
> > What of &?
> >
> > a.each( &->(foo="bar"){puts foo} ) # Ick.
> >
> > Can we drop?
> >
> > a.each( ->(foo="bar"){puts foo} ) # Better.
>
> I was dreaming for a long time of a ruby dialect that has all these
> fancy arrows haskell has. Everybody proposing arrows, please (try to)
> read some haskell code.
>
> But seriosly, I personally would prefer something in the line lambda(x,
> y=1) {...} as it was proposed by other people too.

And here I was wishing for \(foo="bar") {}, the way Haskell does it :)
(Seriously - I've always found that the best of all the lambda
notations)

martin

Martin DeMello

unread,
Oct 12, 2005, 7:42:46 AM10/12/05
to

Why not \ as in Haskell instead? Looks much more like the actual letter
lambda (which is what motivated its use in Haskell) and is two
keystrokes less to type (counting the shift for >).

martin

Christophe Grandsire

unread,
Oct 12, 2005, 7:42:06 AM10/12/05
to
Selon Thomas <sanobas...@yahoo.de>:

>
> I was dreaming for a long time of a ruby dialect that has all these
> fancy arrows haskell has. Everybody proposing arrows, please (try to)
> read some haskell code.
>

I have and can only concur. The arrows make things pretty confusing in most
places.

> But seriosly, I personally would prefer something in the line lambda(x,
> y=1) {...} as it was proposed by other people too.
>

The problem is that "collection.each lambda(foo="bar") {puts foo}" has to be the
ugliest and most long-winded thing I've seen in a long time. It's OK for making
a Proc, but to use as a block it's just plain wrong.

However, it's nearly impossible a problem to solve. Any solution will probably
look rather awful. We just need to find the least offensive one :) . Unless one
finds a way to parse "{|foo="bar"| puts foo}" correctly. That'd be the best
solution.

> The => in the hash syntax is IMHO already one kind of arrow too much.
>

Hasn't a change been accepted that allows one to use ":" as an alternative to
"=>" in hashes?

Hey, what about ":(foo="bar"){puts foo}"? It's still not beautiful but it's
still less annoying, and in Ruby we are already used to see colons at the
beginning of a word. Of course, overloading ":" may not be considered a good
idea, but it shouldn't be a parsing problem as this one would always be
followed by a "(" (and that doesn't happen with symbols). And:

collection.each:(foo="bar"){puts foo}

isn't that bad :) .

Christophe Grandsire

unread,
Oct 12, 2005, 7:44:42 AM10/12/05
to
Selon Martin DeMello <martin...@yahoo.com>:

>
> And here I was wishing for \(foo="bar") {}, the way Haskell does it :)
> (Seriously - I've always found that the best of all the lambda
> notations)
>

I wouldn't mind that one. "\" isn't too instrusive, and as a LaTeX fan I'm quite
used to it. But see my former post on the subject.

Christophe Grandsire

unread,
Oct 12, 2005, 8:06:34 AM10/12/05
to
Selon Martin DeMello <martin...@yahoo.com>:

>
> Why not \ as in Haskell instead? Looks much more like the actual letter
> lambda (which is what motivated its use in Haskell) and is two
> keystrokes less to type (counting the shift for >).
>

Well, keystrokes are keyboard-dependent. At home, to get a \ I have to do an
Alt-Gr (Dutch keyboard:
http://www.microsoft.com/globaldev/keyboards/kbdne.htm). So for me the gain in
only one keystroke, and Alt-Gr / on this keyboard is not always an easy task ;)


Christophe Grandsire

unread,
Oct 12, 2005, 8:16:06 AM10/12/05
to
Selon Christophe Grandsire <christophe...@free.fr>:

>
> Well, keystrokes are keyboard-dependent. At home, to get a \ I have to do an
> Alt-Gr (Dutch keyboard:
> http://www.microsoft.com/globaldev/keyboards/kbdne.htm). So for me the gain
> in
> only one keystroke, and Alt-Gr / on this keyboard is not always an easy task
> ;)
>
>

For some reason, the rest of this message didn't seem to go through. Here it is
again then:

"But that's beside the point. If my idea of using ":" doesn't get off the
ground, I'll be happy to vote for "\". It has a precedent after all."

Devin Mullins

unread,
Oct 12, 2005, 8:26:52 AM10/12/05
to
Christophe Grandsire wrote:

>Hey, what about ":(foo="bar"){puts foo}"? It's still not beautiful but it's
>still less annoying, and in Ruby we are already used to see colons at the
>beginning of a word. Of course, overloading ":" may not be considered a good
>idea, but it shouldn't be a parsing problem as this one would always be
>followed by a "(" (and that doesn't happen with symbols). And:
>
>collection.each:(foo="bar"){puts foo}
>
>isn't that bad :) .
>
>

+1

Devin Mullins

unread,
Oct 12, 2005, 8:27:04 AM10/12/05
to
Trans wrote:

>This still avoids a solution to closing scope for other uses. For
>instance Class.new.
>
> A = Class.new {
> class B
> def x; 1; end
> end
> }
>

> A::B
> (irb):19: warning: toplevel constant B referenced by A::B
>
>

Ho. That is wacky. Same thing for normal constants and for class
variables, of course, 'cept no warning for class variables.

class A
def self.B
Class.new {
@@share = "hello!"
}
end
end
B = A.B
p B.class_eval { @@share } #=> error, uninitialized? wha?
A.class_eval { @@share = 'duck' }
p B.class_eval { @@share } #=> "duck"

You can actually just do Class.new and get the class-variable-sharing
thing -- I just stuffed the block in there 'cause I'm wondering about
the uninitialized part.

C:\Documents and Settings\dlm>irb
irb(main):001:0> Class.new {
irb(main):002:1* @@share = 'hello' }
=> #<Class:0x2cff5a0>
irb(main):003:0> @@share
=> "hello"
irb(main):004:0>

C:\Documents and Settings\dlm>irb
irb(main):001:0> class A
irb(main):002:1> B = Class.new { @@share = 'hello' }
irb(main):003:1> end
=> A::B
irb(main):004:0> A.class_eval { @@share }
NameError: uninitialized class variable @@share in Object
from (irb):4
from (irb):4:in `class_eval'
from (irb):4:in `class_eval'
from (irb):4
irb(main):005:0> A::B.class_eval { @@share }
NameError: uninitialized class variable @@share in Object
from (irb):5
from (irb):5:in `class_eval'
from (irb):5:in `class_eval'
from (irb):5

Wha???

Devin

Daryl Richter

unread,
Oct 12, 2005, 10:00:16 AM10/12/05
to

+1. Furthers Ruby/Smalltalk harmonic convergence. :)

--
Daryl

Berger, Daniel

unread,
Oct 12, 2005, 10:02:30 AM10/12/05
to

-1. Sucks.

Dan


Daniel Tse

unread,
Oct 12, 2005, 10:25:06 AM10/12/05
to
My $0.02:

I feel that the arrow syntax yielding a standalone Proc (my_proc = ->(x)
{ .. }) is distinctly out of place compared to existing Ruby syntax. I
would give my support to turning lambda into a keyword, with the syntax
(my_proc = lambda(x) { ... }) for the simple reason that it is
reminiscent of method call syntax with an accompanying block (for
example open("blah") { |f| ... }).


Yukihiro Matsumoto

unread,
Oct 12, 2005, 10:38:12 AM10/12/05
to
Hi,

In message "Re: Default argument values for blocks"

on Wed, 12 Oct 2005 20:46:53 +0900, Martin DeMello <martin...@yahoo.com> writes:

|Why not \ as in Haskell instead? Looks much more like the actual letter
|lambda (which is what motivated its use in Haskell) and is two
|keystrokes less to type (counting the shift for >).

A backslash is the most unfortunate character, which is caught by yen
sign problem. In Japanese encoding, appearance of the character
varies font to font. On some font (e.g. on my Emacs) it is shown as a
backslash, on other font (e.g. on my Firefox), it is shown as a
Japanese currency sign, Yen (two dashes over captal Y). Indeed, a
backslash can reminds me lambda, but yen sign does not have any clue
for lambda. This must be a tiny problem for non Japanese.

matz.


Yukihiro Matsumoto

unread,
Oct 12, 2005, 10:39:55 AM10/12/05
to
Hi,

In message "Re: Default argument values for blocks"

on Wed, 12 Oct 2005 20:42:06 +0900, Christophe Grandsire <christophe...@free.fr> writes:

|Hey, what about ":(foo="bar"){puts foo}"? It's still not beautiful but it's
|still less annoying, and in Ruby we are already used to see colons at the
|beginning of a word. Of course, overloading ":" may not be considered a good
|idea, but it shouldn't be a parsing problem as this one would always be
|followed by a "(" (and that doesn't happen with symbols). And:
|
|collection.each:(foo="bar"){puts foo}
|
|isn't that bad :) .

I have never thought of that. Hmm, let me think about it during the
conference trip. I'm leaving tomorrow morning.

matz.


Ara.T.Howard

unread,
Oct 12, 2005, 10:48:13 AM10/12/05
to
On Wed, 12 Oct 2005, Yukihiro Matsumoto wrote:

but

method bool ? 42 : (0b101010) { "block" }

is valid now.

':' is nice on the eyes though. maybe '::'

Hugh Sasse

unread,
Oct 12, 2005, 10:59:18 AM10/12/05
to
On Wed, 12 Oct 2005, Ara.T.Howard wrote:
> but
>
> method bool ? 42 : (0b101010) { "block" }
>
> is valid now.
>
> ':' is nice on the eyes though. maybe '::'

maybe :-(foo = "bar") {...}, where :-( is pronounced "sadly"
>
SCNR,
Hugh


Eric Mahurin

unread,
Oct 12, 2005, 11:09:55 AM10/12/05
to
--- Yukihiro Matsumoto <ma...@ruby-lang.org> wrote:

Here's another one:

f = .(foo="bar"){puts foo}

collection.each.(foo="bar){puts foo}

"." is already used for method call, so why not lambda/block
definition? I don't think this would collide with anything
because an identifier should normally follow "." and we are
following it with "(" here.

Christophe Grandsire

unread,
Oct 12, 2005, 11:31:21 AM10/12/05
to
Selon "Ara.T.Howard" <Ara.T....@noaa.gov>:

> >
> > |Hey, what about ":(foo="bar"){puts foo}"? It's still not beautiful but
> it's
> > |still less annoying, and in Ruby we are already used to see colons at the
> > |beginning of a word. Of course, overloading ":" may not be considered a
> good
> > |idea, but it shouldn't be a parsing problem as this one would always be
> > |followed by a "(" (and that doesn't happen with symbols). And:
> > |
> > |collection.each:(foo="bar"){puts foo}
> > |
> > |isn't that bad :) .
> >
> > I have never thought of that. Hmm, let me think about it during the
> > conference trip. I'm leaving tomorrow morning.
>
> but
>
> method bool ? 42 : (0b101010) { "block" }
>
> is valid now.
>

Does it mean "method(bool ? 42 : (0b101010)) { "block"}"? It looks so strange I
don't know how to parse it. Also, doesn't the presence of the "?" make the ":"
unambiguous in this case? Just asking, I really don't know.

Ara.T.Howard

unread,
Oct 12, 2005, 11:53:39 AM10/12/05
to
On Thu, 13 Oct 2005, Christophe Grandsire wrote:

> Selon "Ara.T.Howard" <Ara.T....@noaa.gov>:
>
>>>
>>> |Hey, what about ":(foo="bar"){puts foo}"? It's still not beautiful but
>> it's
>>> |still less annoying, and in Ruby we are already used to see colons at the
>>> |beginning of a word. Of course, overloading ":" may not be considered a
>> good
>>> |idea, but it shouldn't be a parsing problem as this one would always be
>>> |followed by a "(" (and that doesn't happen with symbols). And:
>>> |
>>> |collection.each:(foo="bar"){puts foo}
>>> |
>>> |isn't that bad :) .
>>>
>>> I have never thought of that. Hmm, let me think about it during the
>>> conference trip. I'm leaving tomorrow morning.
>>
>> but
>>
>> method bool ? 42 : (0b101010) { "block" }
>>
>> is valid now.
>>
>
> Does it mean "method(bool ? 42 : (0b101010)) { "block"}"?

yes.

> Also, doesn't the presence of the "?" make the ":" unambiguous in this case?
> Just asking, I really don't know.

probably. i don't know either. just seem potentially confounding.

cheers.

Ezra Zygmuntowicz

unread,
Oct 12, 2005, 12:38:47 PM10/12/05
to

What about:

~:(foo = "bar") {...}

?

-Ezra Zygmuntowicz
Yakima Herald-Republic
WebMaster
http://yakimaherald.com
509-577-7732
ez...@yakima-herald.com

James Edward Gray II

unread,
Oct 12, 2005, 1:10:45 PM10/12/05
to
On Oct 12, 2005, at 10:09 AM, Eric Mahurin wrote:

> Here's another one:
>
> f = .(foo="bar"){puts foo}
>
> collection.each.(foo="bar){puts foo}
>
> "." is already used for method call, so why not lambda/block
> definition? I don't think this would collide with anything
> because an identifier should normally follow "." and we are
> following it with "(" here.

Ooo, I kind-of like that...

James Edward Gray II

Christian Neukirchen

unread,
Oct 12, 2005, 1:50:21 PM10/12/05
to
Yukihiro Matsumoto <ma...@ruby-lang.org> writes:

Imagine a ¥ on it's head... looks quite lambdaish. ;-)

> matz.
--
Christian Neukirchen <chneuk...@gmail.com> http://chneukirchen.org


Christophe Grandsire

unread,
Oct 12, 2005, 3:25:32 PM10/12/05
to
En réponse à Eric Mahurin :

>>|
>>|collection.each:(foo="bar"){puts foo}
>>|
>>|isn't that bad :) .
>>
>>I have never thought of that. Hmm, let me think about it
>>during the
>>conference trip. I'm leaving tomorrow morning.
>
>
> Here's another one:
>
> f = .(foo="bar"){puts foo}
>
> collection.each.(foo="bar){puts foo}
>
> "." is already used for method call, so why not lambda/block
> definition? I don't think this would collide with anything
> because an identifier should normally follow "." and we are
> following it with "(" here.
>

Although I find it kind of attractive, I am concerned about the
overloading of ".", which all in all is a bit small to have much
meaning. I'm afraid it would get unnoticed. ":" I think wouldn't, and
there's already a precedent in Ruby of having a construction begin with
":" (namely symbols). So I kind of like it, but am wondering about its
readability. ":" is similar, but has a higher weight, and is thus better
noticed.

But if my proposal gets struck down, I'll be the first to vote for
yours, since "\" kind of was refused by matz himself because of font issues.
--
Christophe Grandsire.

http://rainbow.conlang.free.fr

You need a straight mind to invent a twisted conlang.


ES

unread,
Oct 12, 2005, 3:28:45 PM10/12/05
to
Christophe Grandsire wrote:
> Selon Thomas <sanobas...@yahoo.de>:
>
>
>>I was dreaming for a long time of a ruby dialect that has all these
>>fancy arrows haskell has. Everybody proposing arrows, please (try to)
>>read some haskell code.
>>
>
>
> I have and can only concur. The arrows make things pretty confusing in most
> places.
>
>
>>But seriosly, I personally would prefer something in the line lambda(x,
>>y=1) {...} as it was proposed by other people too.
>>
>
>
> The problem is that "collection.each lambda(foo="bar") {puts foo}" has to be the
> ugliest and most long-winded thing I've seen in a long time. It's OK for making
> a Proc, but to use as a block it's just plain wrong.

So do not use it as a block. This syntax only solves the default args (etc.)
problem but does not in any way invalidate the block syntax (which, as Matz
has pointed out many times, is not going anywhere).

collection.each {|foo| puts foo}

and

block = lambda(foo = 'bar') { puts foo }

> However, it's nearly impossible a problem to solve. Any solution will probably
> look rather awful. We just need to find the least offensive one :) . Unless one
> finds a way to parse "{|foo="bar"| puts foo}" correctly. That'd be the best
> solution.
>
>
>>The => in the hash syntax is IMHO already one kind of arrow too much.
>>
>
>
> Hasn't a change been accepted that allows one to use ":" as an alternative to
> "=>" in hashes?
>
> Hey, what about ":(foo="bar"){puts foo}"? It's still not beautiful but it's
> still less annoying, and in Ruby we are already used to see colons at the
> beginning of a word. Of course, overloading ":" may not be considered a good
> idea, but it shouldn't be a parsing problem as this one would always be
> followed by a "(" (and that doesn't happen with symbols). And:
>
> collection.each:(foo="bar"){puts foo}
>
> isn't that bad :) .
> --
> Christophe Grandsire.

E

Christophe Grandsire

unread,
Oct 12, 2005, 3:32:06 PM10/12/05
to
En réponse à Ara.T.Howard :

>>
>> Does it mean "method(bool ? 42 : (0b101010)) { "block"}"?
>
>
> yes.
>

Difficult to parse indeed...

>> Also, doesn't the presence of the "?" make the ":" unambiguous in this
>> case?
>> Just asking, I really don't know.
>
> probably. i don't know either. just seem potentially confounding.
>

I'd say it has the same potential of confusion as symbols, since you can
have both ":name" and "bool ? 42 : name". If this isn't considered an
issue (and it seems it isn't :) ), I don't think my proposal would be
one either. Otherwise, I think Eric's proposal might be an idea too
(although in this case *I* am concerned about possibilities of confusion
by lack of notice of the symbol).

But matz said he would think about it. I'm really honoured already, and
I don't mind that much if it doesn't make it, as long as we get an
aesthetic and practical syntax.
--
Christophe Grandsire.

http://rainbow.conlang.free.fr

You need a straight mind to invent a twisted conlang.


Christophe Grandsire

unread,
Oct 12, 2005, 3:34:45 PM10/12/05
to
En réponse à Yukihiro Matsumoto :

> |
> |collection.each:(foo="bar"){puts foo}
> |
> |isn't that bad :) .
>
> I have never thought of that. Hmm, let me think about it during the
> conference trip. I'm leaving tomorrow morning.
>
> matz.
>

I'm really honoured that you're considering my proposal. I can hardly
wait to know what your opinion is!

Sean O'Halpin

unread,
Oct 12, 2005, 4:47:21 PM10/12/05
to
On 10/12/05, Ara.T.Howard <Ara.T....@noaa.gov> wrote:
> but
>
> method bool ? 42 : (0b101010) { "block" }
>
> is valid now.
Hmmm... this is what I get. Have I missed something?

def method(bool)
bool
end

method true ? 42 : (0b101010) { "block" }
method false ? 42 : (0b101010) { "block" }

__END__
block-syntax.rb:5: syntax error
method true ? 42 : (0b101010) { "block" }
^
(The "^" points at the space after the "{" )

Regards,

Sean


Sean O'Halpin

unread,
Oct 12, 2005, 5:18:32 PM10/12/05
to
On 10/12/05, Eric Mahurin <eric_m...@yahoo.com> wrote:
> Or maybe if "eval" became a keyword like you mentioned above
> and it could also take a block, you could do this instead:
>
> b=1
> eval {|;b|
> b=5
> p b # => 5
> }
> p b # => 1

+1

Any chance of eval taking a block ~and~ a specific binding, e.g.

eval &block, binding

(though this breaks current argument parsing rules).

Sean


Ara.T.Howard

unread,
Oct 12, 2005, 5:44:54 PM10/12/05
to

eval(binding, &block) works. the eval(string) method just needs to check it's
arg type.

itsme213

unread,
Oct 12, 2005, 6:32:35 PM10/12/05
to

"Christophe Grandsire" <christophe...@free.fr> wrote in message

> collection.each:(foo="bar"){puts foo}

+1


Eric Mahurin

unread,
Oct 12, 2005, 6:38:43 PM10/12/05
to
--- "Ara.T.Howard" <Ara.T....@noaa.gov> wrote:

> On Thu, 13 Oct 2005, Sean O'Halpin wrote:
>
> > On 10/12/05, Eric Mahurin <eric_m...@yahoo.com> wrote:
> >> Or maybe if "eval" became a keyword like you mentioned
> above
> >> and it could also take a block, you could do this instead:
> >>
> >> b=1
> >> eval {|;b|
> >> b=5
> >> p b # => 5
> >> }
> >> p b # => 1
> >
> > +1
> >
> > Any chance of eval taking a block ~and~ a specific binding,
> e.g.
> >
> > eval &block, binding
> >
> > (though this breaks current argument parsing rules).
> >
> > Sean
>
> eval(binding, &block) works. the eval(string) method just
> needs to check it's
> arg type.

It doesn't need to check type. If there is a block, the
optional arg would be a binding. Otherwise, the first arg is
the eval string and the optional second arg is the binding.

If this is possible, it would be good to be able to do this to
a general Proc. But, if not you could still make the
functionality with the above Kernel#eval:

class Proc
def rebind(binding)
Proc.new {
eval(binding,&self)
}
end
end

Of course you have the same problem that we have with
instance_eval - you can't pass any args. Might as well think
about making that work with eval too.



__________________________________
Yahoo! Music Unlimited
Access over 1 million songs. Try it free.
http://music.yahoo.com/unlimited/


David A. Black

unread,
Oct 12, 2005, 7:17:34 PM10/12/05
to
Hi --

On Wed, 12 Oct 2005, Christophe Grandsire wrote:

> However, it's nearly impossible a problem to solve. Any solution will probably
> look rather awful. We just need to find the least offensive one :) . Unless one
> finds a way to parse "{|foo="bar"| puts foo}" correctly. That'd be the best
> solution.

>
>> The => in the hash syntax is IMHO already one kind of arrow too much.
>>
>
> Hasn't a change been accepted that allows one to use ":" as an alternative to
> "=>" in hashes?
>
> Hey, what about ":(foo="bar"){puts foo}"? It's still not beautiful but it's
> still less annoying, and in Ruby we are already used to see colons at the
> beginning of a word. Of course, overloading ":" may not be considered a good
> idea, but it shouldn't be a parsing problem as this one would always be
> followed by a "(" (and that doesn't happen with symbols). And:
>

> collection.each:(foo="bar"){puts foo}
>

> isn't that bad :) .

But it's so arbitrary. Surely there's no general principle of "being
used to" a given punctuation mark that makes it acceptable for
something like this.

I don't mean to jump on your idea specifically. The whole thread
seems to be about which arbitrary bit of punctuation might be least
ugly. I'm totally unconvinced that default values for block variables
are worth doing any of them.


David (in San Diego! :-)

--
David A. Black
dbl...@wobblini.net


Sean O'Halpin

unread,
Oct 12, 2005, 7:31:15 PM10/12/05
to
On 10/12/05, Eric Mahurin <eric_m...@yahoo.com> wrote:
> --- "Ara.T.Howard" <Ara.T....@noaa.gov> wrote:
>
> > On Thu, 13 Oct 2005, Sean O'Halpin wrote:
> >
> > > On 10/12/05, Eric Mahurin <eric_m...@yahoo.com> wrote:
> > >> Or maybe if "eval" became a keyword like you mentioned
> > above
> > >> and it could also take a block, you could do this instead:
> > >>
> > >> b=1
> > >> eval {|;b|
> > >> b=5
> > >> p b # => 5
> > >> }
> > >> p b # => 1
> > >
> > > +1
> > >
> > > Any chance of eval taking a block ~and~ a specific binding,
> > e.g.
> > >
> > > eval &block, binding
> > >
> > > (though this breaks current argument parsing rules).
> > >
> > > Sean
> >
> > eval(binding, &block) works. the eval(string) method just
> > needs to check it's
> > arg type.

Agreed - I did think of that but for some reason I wasn't sure it felt
right. We'd have eval(string, binding) but eval(binding, &block).
Still, I guess anyone who wanted to use eval(binding, &block) would
probably know what they're doing! Both your and Eric's suggestions
have made me change my mind. I'm sure it would be easier to implement
this than to change Ruby's parser.

(BTW: Just in case anyone gets the wrong idea here, Ara is saying that
eval(binding, &block) doesn't break arg parsing rules - don't expect
this to actually ~work~ in Ruby 1.8.2!)

>
> It doesn't need to check type. If there is a block, the
> optional arg would be a binding. Otherwise, the first arg is
> the eval string and the optional second arg is the binding.
>
> If this is possible, it would be good to be able to do this to
> a general Proc. But, if not you could still make the
> functionality with the above Kernel#eval:
>
> class Proc
> def rebind(binding)
> Proc.new {
> eval(binding,&self)
> }
> end
> end
>
> Of course you have the same problem that we have with
> instance_eval - you can't pass any args. Might as well think
> about making that work with eval too.

For instance_eval, how about simply

instance_eval(*args, &block)

i.e. if it has a block, then the arguments are passed to it.
e.g.

instance_eval(1,2,3) {|a,b,c| ...}
instance_eval(1,2,3, &block)

If no block, then it would expect a string as it does now.

For eval, this could work the same way, with the first argument being
the binding, e.g.

eval(binding, 1,2,3) {|a,b,c| ... }

As Eric says, the distinguishing characteristic would be whether there
is a block or not.

Regards,

Sean


Phil Tomson

unread,
Oct 12, 2005, 11:58:38 PM10/12/05
to

I totally agree, David. I can't believe that we're about to mess up
Ruby's syntax because someone asked for default values for block
variables. I hope this idea is really well discussed at Rubyconf. I
can't think of a time that I thought "you know, I really could use to
have default values for block variables". Since it is such a special
case and it's easy to work around I can't see messing with one of the
most recognizable bits or Ruby syntax (as in, if I see
"array.each{|foo| ... }" I know immediately I'm looking at Ruby code).

There's a discussion of this over at http://Redhanded.hobix.com where
the assumption seems to be that this proposed '->' syntax is going to
replace the current 'goalpost' syntax '{|..|}'. Someone please say
this isn't so.


Phil

ES

unread,
Oct 13, 2005, 12:02:07 AM10/13/05
to
ES wrote:
> Christophe Grandsire wrote:
>
>> Selon Thomas <sanobas...@yahoo.de>:
>>
>>
>>> I was dreaming for a long time of a ruby dialect that has all these
>>> fancy arrows haskell has. Everybody proposing arrows, please (try to)
>>> read some haskell code.
>>>
>>
>>
>> I have and can only concur. The arrows make things pretty confusing in
>> most
>> places.
>>
>>
>>> But seriosly, I personally would prefer something in the line lambda(x,
>>> y=1) {...} as it was proposed by other people too.
>>>
>>
>>
>> The problem is that "collection.each lambda(foo="bar") {puts foo}" has
>> to be the
>> ugliest and most long-winded thing I've seen in a long time. It's OK
>> for making
>> a Proc, but to use as a block it's just plain wrong.
>
>
> So do not use it as a block...

I am terribly sorry, that came out entirely too harsh. There was supposed
to be a smiley face right there!

> ...This syntax only solves the default args (etc.)

Christophe Grandsire

unread,
Oct 13, 2005, 12:39:04 AM10/13/05
to
En réponse à David A. Black :

>
> But it's so arbitrary. Surely there's no general principle of "being
> used to" a given punctuation mark that makes it acceptable for
> something like this.
>

No, but do you really want to have "->" instead?

> I don't mean to jump on your idea specifically. The whole thread
> seems to be about which arbitrary bit of punctuation might be least
> ugly. I'm totally unconvinced that default values for block variables
> are worth doing any of them.
>

The problem is that default values for blocks *are* now in Ruby 1.9, and
thus are probably going to be in Ruby2, and use right now the ugly "->".
If they are going to be there, let's have at least a non-intrusive
syntax. Yes it's arbitrary, but just as much as using : for symbols and
@ for instance variables. At the end of the day, every syntax in a
language is a matter of choice and convention, i.e. it's arbitrary.

I also don't really see why blocks arguments should have default values.
But if we're going to have them, at least let's have an OK syntax for
them, instead of an ugly beast.

Caleb Clausen

unread,
Oct 13, 2005, 1:33:08 AM10/13/05
to
Ok, this has been bugging me ever since the last time this issue came
up on redhanded.

I think that what we'd all like to see, ideally, is a default argument
syntax that looks like default arguments in def headers do. That is:

proc {|a=expr| ... }

This creates an ambiguity if expr contains an |-operator. Which should
be resolved by requiring parentheses around the expression in that
case. This seemed like it ought to be pretty easy to implement.... so
I tried to see if I could get my RubyLexer to support the above
syntax. And, it took only about 15 minutes to code and test a tweak to
RubyLexer to make it all work right. (Actually, there's a small
problem with my tweak as currently written; it ought to be possible to
escape | with a dot as well as parentheses.... but that'd be even
easier to fix.)

(It may seem strange that I decided to address this in a _lexer_ since
it's really a _parsing_ problem. However, RubyLexer also has to be
half-a-parser, since it's a stand-alone lexer. Normally, lexers get
hints from their parsers about what the context is for the current
token; I wanted (perhaps foolishly, as it created a big pile of extra
work) to have RubyLexer work correctly in all cases even if there is
no parser. So, it is actually appropriate to hack RubyLexer to handle
this case.)

Flushed from my success with RubyLexer, I decided to see if I could
repeat it in ruby 1.9's yacc grammar. After some false starts, I
figured out that resolving the ambiguity meant throwing in a %prec
modifier for the right rule... and I found the rule in need of
hackery: any rule with |-as-goalpost should be very high precedence in
order to avoid the interpretation of |-as-operator.

But no matter how many different variations I tried, I could not get
ruby to build correctly again after tossing in a %prec (and modifying
the block argument list to accept default parameters). I don't
remember the details now... it might have been dieing merely because I
had made no effort to ensure that whatever comes after the parser is
able to understand the new syntax tree format that this change
necessitates. However, my now vague memory of this is that the error
seemed to be in the parser itself.

A little reflection should have shown me the futility.... Presumably
Matz and Nobu have tried all this already and been frustrated by the
same obstacle that I had been beating my brain bloody against. Why
should I, with my pathetic and measly yacc skills, expect to do any
better?

But... does anyone know why I couldn't get yacc to do what was so easy
in my hand-coded lexer? I've long since erased my yacc hacks in
disgust, but if anyone's interested enough to want to see them, they
can easily be reproduced.


Clifford Heath

unread,
Oct 13, 2005, 2:03:26 AM10/13/05
to
Caleb Clausen wrote:
> But... does anyone know why I couldn't get yacc to do what was so easy
> in my hand-coded lexer? I've long since erased my yacc hacks in
> disgust, but if anyone's interested enough to want to see them, they
> can easily be reproduced.

I forget the details now, but C has the same problem with the comma
operator, when it occurs in a function-call parameter list - the
precedence changes. You might see how that is handled in one of the
many yacc grammars for C.

FWIW, I think that the goalpost symbol was a bad choice by matz, but
regardless of that, you're aiming at the right work-around.

Clifford Heath.

Trans

unread,
Oct 13, 2005, 2:42:16 AM10/13/05
to

Christophe Grandsire wrote:
> collection.each:(foo="bar"){puts foo}

Ha! How ironic, I thought of that last night too. But after playing
with I decided I did not like it. The colon has too much "seperation"
semantic, I think. And think of the Python converts ;) Indeed I have. I
was thinking that the colon might be a nice way to go without 'do':

collection.each:
puts "foo"
end

With todays kind of block arguments:

collection.each: |foo|
puts foo
end

But we're after outer arguments, so with Matz/Perl notation:

collection.each->(foo):
puts foo
end

I've tried every punctuation combination I can think of. I think I like
that best. Though I might suggest a word form for those who do not:

collection.each fn(foo):
puts foo
end

T.

Thomas

unread,
Oct 13, 2005, 3:36:40 AM10/13/05
to
> Mostly because yacc does not allow it. It confuses
>
> lambda { |foo = bar| puts foo }
>
> as
>
> lambda { |foo = (bar| puts foo) }
>
> and causes syntax error.

(Mostly) out of curiosity:

Would this

whatever_method {(x, foo=bar) puts x,foo}

and also this

whatever_method do(x, foo=bar)
puts x,foo
end

be possible.

Cheers,
Thomas.

Phil Tomson

unread,
Oct 13, 2005, 3:41:31 AM10/13/05
to

Christophe Grandsire wrote:
> En réponse à David A. Black :
> >
> > But it's so arbitrary. Surely there's no general principle of "being
> > used to" a given punctuation mark that makes it acceptable for
> > something like this.
> >
>
> No, but do you really want to have "->" instead?

I think the other option is to pass on the whole idea of default
arguments to blocks for now if we can't get the nice lambda
{|foo='bar'| puts foo } sort of syntax to work. The idea could be
resurrected later when we have a better parser technology. Why open
the door for this arrow operator for this very special (and likely very
rarely used) case.

>
> > I don't mean to jump on your idea specifically. The whole thread
> > seems to be about which arbitrary bit of punctuation might be least
> > ugly. I'm totally unconvinced that default values for block variables
> > are worth doing any of them.
> >
>
> The problem is that default values for blocks *are* now in Ruby 1.9, and
> thus are probably going to be in Ruby2,

1.9 is a testing ground for ideas for Ruby2 (at least that's how I
understand it). I don't think that everything in 1.9 (as it currently
stands) will be exactly as it is in 2.0.

> and use right now the ugly "->".
> If they are going to be there, let's have at least a non-intrusive
> syntax. Yes it's arbitrary, but just as much as using : for symbols and
> @ for instance variables. At the end of the day, every syntax in a

> language is a matter of choice and convo ention, i.e. it's arbitrary.

Sure that's true, however, it doesn't seem like a good idea to
introduce a whole new syntax to support a feature that seems to have
limited utility. Especially when the new syntax essentially introduces
a new and very different way to define blocks (a central feature of
Ruby).

>
> I also don't really see why blocks arguments should have default values.
> But if we're going to have them, at least let's have an OK syntax for
> them, instead of an ugly beast.

As I said above, I think that if we can't have the syntax that most
everyone agrees is the most pleasant and the one which causes the least
disruption ( {|foo='bar'| } ) in that it doesn't introduce a special
case then perhaps we should forgo the support for the feature until we
can get the syntax that fits best with the way things are done now.
I'd just hate to see this '->' thingy introduced and in all the Ruby
books and then someone comes along and figures out how to parse the
pathological case: {|foo=a|b| } (something very hard and perhaps
impossible in yacc, but who knows what some yacc wizard might be able
to come up with?). Then what? do we deprecate '->'? Probably not,
because there will be code out in the wild that depends on it. At that
point we have to live with it.

Phil

Thomas

unread,
Oct 13, 2005, 3:44:20 AM10/13/05
to
> whatever_method {(x, foo=bar) puts x,foo}
>
> and also this
>
> whatever_method do(x, foo=bar)
> puts x,foo
> end

Or

Christophe Grandsire

unread,
Oct 13, 2005, 4:40:33 AM10/13/05
to
Selon Phil Tomson <philt...@gmail.com>:

>
> I think the other option is to pass on the whole idea of default
> arguments to blocks for now if we can't get the nice lambda
> {|foo='bar'| puts foo } sort of syntax to work. The idea could be
> resurrected later when we have a better parser technology. Why open
> the door for this arrow operator for this very special (and likely very
> rarely used) case.
>

True. I'd rather have it like that too. But it seems a sizeable amount of people
*want* default block argument values and aren't willing to wait until Ruby3. So
if we *have* to have this new syntax, at least let's not use the arrow and let
us find a better syntax. If at the end the whole idea is thrown away and Ruby2
doesn't support it, it won't be a problem anyway. I just want to secure the
ground in the case the syntax finds its way into Ruby2. Better safe than sorry.

>
> 1.9 is a testing ground for ideas for Ruby2 (at least that's how I
> understand it). I don't think that everything in 1.9 (as it currently
> stands) will be exactly as it is in 2.0.
>

No, not their look and feel in any case. But for the case it would stay, let us
work out a "least ugly" syntax.

>
> Sure that's true, however, it doesn't seem like a good idea to
> introduce a whole new syntax to support a feature that seems to have
> limited utility. Especially when the new syntax essentially introduces
> a new and very different way to define blocks (a central feature of
> Ruby).
>

I completely agree. But once again you argue at cross-purpose from me. I'd
rather do without default block argument values until we find a parser that
does "{ |foo=bar| ... }" correctly. But since the feature seems to be seen of
enough importance to have found its way in Ruby 1.9 already, in a way that I
find too ugly for words, I find it more productive to propose an alternative
rather than just say that I don't want the feature at all. Once again, I'd
prefer not have the new syntax at all, but if we are to have it at least have
something that isn't too ugly.

>
> As I said above, I think that if we can't have the syntax that most
> everyone agrees is the most pleasant and the one which causes the least
> disruption ( {|foo='bar'| } ) in that it doesn't introduce a special
> case then perhaps we should forgo the support for the feature until we
> can get the syntax that fits best with the way things are done now.

It's OK by me. But I was under the impression that this had been discussed
already and that it was decided to use default block argument values anyway.

> I'd just hate to see this '->' thingy introduced and in all the Ruby
> books and then someone comes along and figures out how to parse the
> pathological case: {|foo=a|b| } (something very hard and perhaps
> impossible in yacc, but who knows what some yacc wizard might be able
> to come up with?). Then what? do we deprecate '->'? Probably not,
> because there will be code out in the wild that depends on it. At that
> point we have to live with it.
>

Exactly! Hence my proposal for ":". At least we do *not* introduce a completely
new symbol (Eric's proposal of "." is also good for this purpose). As for
deprecating features, it can be done. I doubt after Ruby2 is out that the
language will not evolve anymore to a point where compatibility-breaking
changes won't have to be added (like they are at the moment for Ruby2).
Deprecating features can be done then.

We agree on many things. The only thing we disagree on is whether it is useful
to discuss a new syntax we actually don't want to appear in the language. You
say it's not, and we should just argue against the whole feature if we can't get
it without a whole new syntax. I say it is, because the fact that there is a
discussion means there *is* a chance that the new syntax will find its way into
Ruby2, in which case I'd rather have it in a way I can live with rather than in
a way that I cannot.
--
Christophe Grandsire.

http://rainbow.conlang.free.fr

It takes a straight mind to create a twisted conlang.


Christophe Grandsire

unread,
Oct 13, 2005, 4:58:19 AM10/13/05
to
Selon Thomas <sanobas...@yahoo.de>:

>
> whatever_method do(x, foo=bar) {puts x,foo}
>

Despite the fact that it looks like a monstruous cross between do... end and
{...}, and would allow the stuttering:

whatever_method do(x, foo=bar) do puts x,foo end

I don't find it that bad at all. If we go for a keyword rather than symbol
solution, I wouldn't mind it. For returning a Proc, using lambda is still the
best idea so far:

a = lambda(x, foo=bar) {puts x,foo}

Maybe "with"?

whatever_method with(x, foo=bar) {puts x,foo}
whatever_method with(x, foo=bar) do puts x,foo end

I still like my colon better ;) .

Thomas Sondergaard

unread,
Oct 13, 2005, 5:35:11 AM10/13/05
to
Yukihiro Matsumoto wrote:
> Hi,
>
> In message "Re: Default argument values for blocks"
> on Wed, 12 Oct 2005 10:13:31 +0900, "David A. Black" <dbl...@wobblini.net> writes:
>
> |I definitely think a keyword would be better than -> .
>
> Maybe. Some prefer verbosity to clarity. So what keyword you think
> "the best"?
>
> matz.

Instead of introducing a new keyword for lambdas wouldn't it be simpler
to introduce a new assignment operator for default arguments, e.g :=

nobuyoshi nakada

unread,
Oct 13, 2005, 6:29:00 AM10/13/05
to
Hi,

At Thu, 13 Oct 2005 14:33:08 +0900,
Caleb Clausen wrote in [ruby-talk:160349]:


> A little reflection should have shown me the futility.... Presumably
> Matz and Nobu have tried all this already and been frustrated by the
> same obstacle that I had been beating my brain bloody against. Why
> should I, with my pathetic and measly yacc skills, expect to do any
> better?

Me? I'd tried it once by differentiating goal-post from
bit-or in the lexer.

http://www.rubyist.net/~nobu/t/20050805.html#p01

I don't remember the detail too, however the essential idea
seems to be adopted partly.

--
Nobu Nakada


Eric Mahurin

unread,
Oct 13, 2005, 9:36:16 AM10/13/05
to

Anybody ever just consider making a new expression (or maybe
RHS?) rule just for these default values such that "|" was not
in this expression? (...) in this or-less expression would
still use the normal expression. Wouldn't this solve the
problem? You'd just be forced to use (...) whenever you wanted
to "|". That doesn't seem so bad.

.. { |a,b=1|2|a*b } # b default: 1, code: 2|a*b
.. { |a,b=(1|2)|a*b } # b default: (1|2), code: a*b
.. { |a,b=1+2|a*b } # b default: 1+2, code: a*b

I don't see any ambiguity doing it this way.

Of course the other reason for the new syntax is a shortented
lambda syntax. I'd say just to do what was being done
previously in 1.9: use {} and resolve ambiguities with {} hash.
The simple solution to resolve ambiguities is in this lambda,
require ||. If you didn't want the ||, you would have to use
the equivalent: {|*| ... }. When the parser encounters a "{",
you only have to lookahead one token to see whether it is a
lambda (next token: "|") or a hash (next token: not a "|").

Another option for a shortened lambda is to put some symbol
(that doesn't make sense in front of a hash) in front of a
block to make it a lambda. A few options for that would be: &{
}, \{ }, .{ }, ^{ }. You may even be able to treat some of
these as simply another Kernel method (alias for lambda).


__________________________________________________
Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around
http://mail.yahoo.com


David A. Black

unread,
Oct 13, 2005, 9:46:42 AM10/13/05
to
Hi --

On Thu, 13 Oct 2005, Eric Mahurin wrote:

> Of course the other reason for the new syntax is a shortented
> lambda syntax. I'd say just to do what was being done
> previously in 1.9: use {} and resolve ambiguities with {} hash.
> The simple solution to resolve ambiguities is in this lambda,
> require ||. If you didn't want the ||, you would have to use
> the equivalent: {|*| ... }. When the parser encounters a "{",
> you only have to lookahead one token to see whether it is a
> lambda (next token: "|") or a hash (next token: not a "|").

No, please not that. I want to know, when I look at:

obj.meth {

exactly what it is, as I can now. I don't want to have to read ahead
to the secret punctuation signal.

There must be some way out of this that doesn't involve adding all
sorts of significant punctuation to the language. Or is there? I'm
starting to wonder whether maybe Ruby has hit the point where, short
of \&*{[ and friends, there are no ways left to represent all the
states and options people want. I literally can't remember the last
time an enhancement (other than just a method addition) was suggested
that didn't involve more punctuation.

I think Ruby's cleanness of line is a *major* reason that people are
attracted to Ruby, and it won't take more than a few new punctuation
workarounds to make a serious dent in that look.


David

Christophe Grandsire

unread,
Oct 13, 2005, 9:57:04 AM10/13/05
to
Selon Eric Mahurin <eric_m...@yahoo.com>:

>
> Anybody ever just consider making a new expression (or maybe
> RHS?) rule just for these default values such that "|" was not
> in this expression? (...) in this or-less expression would
> still use the normal expression. Wouldn't this solve the
> problem? You'd just be forced to use (...) whenever you wanted
> to "|". That doesn't seem so bad.
>

> ... { |a,b=1|2|a*b } # b default: 1, code: 2|a*b
> ... { |a,b=(1|2)|a*b } # b default: (1|2), code: a*b
> ... { |a,b=1+2|a*b } # b default: 1+2, code: a*b


>
> I don't see any ambiguity doing it this way.
>

Yacc does. Even the simple { |a,b=1| a*b } fails because Yacc treats it as { |
a,b=(1| a*b) }. And that *cannot* be solved in the current state of Yacc. The
problem is that there doesn't seem to be *any* solution that solves both this
problem and the problem of allowing bitwise or's in default arguments, short of
renaming the bitwise or, which would be such a compatibility break that it isn't
worth contemplating.

This is at least my understanding of the problem.

Eric Mahurin

unread,
Oct 13, 2005, 11:04:02 AM10/13/05
to

Are you saying this from experience? It sounds like it, but
your last statement says not. Don't be so authoritative if you
are not.

Take a look at the parse.y code. Look at the "arg" rule.
That's where the action is. All I'm suggesting is that this
entire rule be duplicated and renamed (and all immediate
recursive calls to itself). Maybe "arg2". And then in this
new rule, this alternative would be deleted:

| arg '|' arg
{
/*%%%*/
$$ = call_op($1, '|', 1, $3);
/*%
$$ = dispatch3(binary, $1, ID2SYM('!'), $3);
%*/
}

Then in the new block args definition, you'd allow optional
arguments (something like f_opt) which would call this "arg2"
instead of "arg".

When I get a chance, I might try this.

Austin Ziegler

unread,
Oct 13, 2005, 11:17:40 AM10/13/05
to
On 10/13/05, Christophe Grandsire <christophe...@free.fr> wrote:
> Yacc does. Even the simple { |a,b=1| a*b } fails because Yacc treats it as { |
> a,b=(1| a*b) }. And that *cannot* be solved in the current state of Yacc. The
> problem is that there doesn't seem to be *any* solution that solves both this
> problem and the problem of allowing bitwise or's in default arguments, short of
> renaming the bitwise or, which would be such a compatibility break that it isn't
> worth contemplating.
>
> This is at least my understanding of the problem.

Is there any particular reason that we can't use a different parser,
e.g., Coco or something else? Surely there's got to be something
better than Yacc by now.

-austin
--
Austin Ziegler * halos...@gmail.com
* Alternate: aus...@halostatue.ca


Lionel Thiry

unread,
Oct 13, 2005, 12:20:12 PM10/13/05
to
Ara.T.Howard a écrit :

> On Wed, 12 Oct 2005, Yukihiro Matsumoto wrote:
>
>> Hi,
>>
>> In message "Re: Default argument values for blocks"
>> on Wed, 12 Oct 2005 20:42:06 +0900, Christophe Grandsire

>> <christophe...@free.fr> writes:
>>
>> |Hey, what about ":(foo="bar"){puts foo}"? It's still not beautiful
>> but it's
>> |still less annoying, and in Ruby we are already used to see colons at
>> the
>> |beginning of a word. Of course, overloading ":" may not be considered
>> a good
>> |idea, but it shouldn't be a parsing problem as this one would always be
>> |followed by a "(" (and that doesn't happen with symbols). And:
>> |
>> |collection.each:(foo="bar"){puts foo}
>> |
>> |isn't that bad :) .
>>
>> I have never thought of that. Hmm, let me think about it during the
>> conference trip. I'm leaving tomorrow morning.

>
>
> but
>
> method bool ? 42 : (0b101010) { "block" }
>
> is valid now.

Why would it be?

method bool ? 42 : :(0b101010) { "block" }

>
> ':' is nice on the eyes though. maybe '::'
>


--
Lionel Thiry

Personal web site: http://users.skynet.be/lthiry/

gabriele renzi

unread,
Oct 13, 2005, 1:56:28 PM10/13/05
to
Austin Ziegler ha scritto:

I remember matz talking about ANTLR long time ago, AFAIR he said
something realted to ANTLR, I think he said that while it could be fast,
thread safe and a lot of nice things there were some problems on the
programmer side (maybe lack of knowledge, I can't remember well).

OTOH I think the people trying to rewrite a ruby parser with COCO had
some problems too (think of ParseTree).

Phil Tomson

unread,
Oct 13, 2005, 1:56:28 PM10/13/05
to

Austin Ziegler wrote:
> On 10/13/05, Christophe Grandsire <christophe...@free.fr> wrote:
> > Yacc does. Even the simple { |a,b=1| a*b } fails because Yacc treats it as { |
> > a,b=(1| a*b) }. And that *cannot* be solved in the current state of Yacc. The
> > problem is that there doesn't seem to be *any* solution that solves both this
> > problem and the problem of allowing bitwise or's in default arguments, short of
> > renaming the bitwise or, which would be such a compatibility break that it isn't
> > worth contemplating.
> >
> > This is at least my understanding of the problem.
>
> Is there any particular reason that we can't use a different parser,
> e.g., Coco or something else? Surely there's got to be something
> better than Yacc by now.
>

While I tend to agree that there are probably much better parser
generators available now like ANTLR or even using a Ruby-based one like
Rockit, I can understand the hesitation to change from yacc. It's a
huge amount of work for one, and there would need to be a lot of
testing to ensure that nothing has broke. I suspect that a change from
yacc to another parser generator would delay Ruby2.0 by at least
several months. Maybe that would be OK. Perhaps there would be other
advantages gained by moving away from yacc that would help justify
doing so?

I'm still in the "It might be a nice feature to have, but it's not
really needed enough to justify the kinds of changes being suggested"
category.

Phil

Austin Ziegler

unread,
Oct 13, 2005, 2:38:10 PM10/13/05
to
On 10/13/05, Phil Tomson <philt...@gmail.com> wrote:
> While I tend to agree that there are probably much better parser
> generators available now like ANTLR or even using a Ruby-based one like
> Rockit, I can understand the hesitation to change from yacc. It's a
> huge amount of work for one, and there would need to be a lot of
> testing to ensure that nothing has broke. I suspect that a change from
> yacc to another parser generator would delay Ruby2.0 by at least
> several months. Maybe that would be OK. Perhaps there would be other
> advantages gained by moving away from yacc that would help justify
> doing so?
>
> I'm still in the "It might be a nice feature to have, but it's not
> really needed enough to justify the kinds of changes being suggested"
> category.

I'm suggesting that it may be time for a parser change because the
proposed language changes IMO are really really really ugly -- and I'd
rather see:

foo = lambda { |foo = 1 | 2| puts foo }

work than not.

Eric Mahurin

unread,
Oct 13, 2005, 3:03:17 PM10/13/05
to

How do you interpret the above?

foo = lambda { |foo = 1| (2|puts foo) }

or

foo = lambda { |foo = (1|2)| puts foo }

I think the first interpretation is implementable in most
parsers (including yacc, I think) relatively easily if you just
don't allow "|" directly in the default value (unlike a normal
RHS). The second interpretation would be more difficult
because it would require an arbitrary amount of lookahead.
Even if the parser can do it, I think arbitrary amounts of
lookahead should be avoided in a language because it will
result in a performance hit (like backtracking in regular
expressions).



__________________________________
Yahoo! Mail - PC Magazine Editors' Choice 2005
http://mail.yahoo.com


Christophe Grandsire

unread,
Oct 13, 2005, 3:25:51 PM10/13/05
to
En réponse à Eric Mahurin :

>
> Are you saying this from experience? It sounds like it, but
> your last statement says not. Don't be so authoritative if you
> are not.
>

Not experience but this:
http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-talk/160045
Is that authority enough for you? If matz says it doesn't work, I'd say
he knows what he is talking about. It's his language after all, he has
spent more time on it than anybody else.

> Take a look at the parse.y code.

I wouldn't understand it anyway, I don't know enough C. But when I'm
basically repeating what matz says, I do expect that it has some
authority, and then I add a disclaimer because I can always
misunderstand people. In this case I didn't. What I said was exactly
what matz said.
--
Christophe Grandsire.

http://rainbow.conlang.free.fr

You need a straight mind to invent a twisted conlang.


Phil Tomson

unread,
Oct 13, 2005, 4:28:10 PM10/13/05
to

I'm not a parser expert, but wouldn't the second example you pose be
helped by the fact that you've enclosed the '1|2' expression in parens?
wouldn't that expression within the parens be evaluated first and the
resulting value substituted into the 'foo = ' expression?

I ask because a lot of people have suggested that requiring enclosing
bitwise OR expressions in parens in the block param would solve the
problem.

I don't see any way to do the following without lookahead:

foo = lambda { |foo = 1|2|3| puts foo }

And as you say the more lookahead you're doing, the slower the parser
will be.

The goalposts are problematic for this sort of thing. What about an
alternative (some have been suggested):

lambda{ (foo = 1|2) puts foo }

If that one is problematic, then maybe:
lambda{ |(foo = 1|2, bar = foo|3)| puts foo, bar }

This one was proposed long ago as a way to declare a var whose scope is
outside the block:


lambda { <foo = 1|2> puts foo }


But again, I think we should hold out for the 'ideal' syntax or just
forget about the proposed feature.

Phil

Trans

unread,
Oct 13, 2005, 4:44:20 PM10/13/05
to
>This one was proposed long ago as a way to declare a var whose scope is
> outside the block:
>
> lambda { <foo = 1|2> puts foo }

All sorts of things can work, one that looks quite nice:

lambda { foo = 1|2 -> puts foo }

But I would suggest that everyone give the -> () {} notation chance. I
really hated it at first too, but it has grown on me and I am starting
to like it even more then goal posts b/c of the way it brings the
parameters outside of the block.

T.

Gyoung-Yoon Noh

unread,
Oct 13, 2005, 4:59:18 PM10/13/05
to
On 10/12/05, Yukihiro Matsumoto <ma...@ruby-lang.org> wrote:
> Hi,
>
> In message "Re: Default argument values for blocks"
> on Wed, 12 Oct 2005 20:42:06 +0900, Christophe Grandsire <christophe...@free.fr> writes:
>
> |Hey, what about ":(foo="bar"){puts foo}"? It's still not beautiful but it's
> |still less annoying, and in Ruby we are already used to see colons at the
> |beginning of a word. Of course, overloading ":" may not be considered a good
> |idea, but it shouldn't be a parsing problem as this one would always be
> |followed by a "(" (and that doesn't happen with symbols). And:
> |
> |collection.each:(foo="bar"){puts foo}
> |
> |isn't that bad :) .
>
> I have never thought of that. Hmm, let me think about it during the
> conference trip. I'm leaving tomorrow morning.
>
> matz.
>
>

+1

collection.each : (foo="bar") { puts foo }

It looks like 'when condition : expression' branch in
'case' statement.

--
http://nohmad.sub-port.net


Eric Mahurin

unread,
Oct 13, 2005, 5:21:02 PM10/13/05
to

Notice the word "interpretation" in what I said. Those were
the 2 interpretations for that example Austin gave above.

David A. Black

unread,
Oct 13, 2005, 5:51:04 PM10/13/05
to
Hi --

But why would you want a method call and argument list and block to
look like when condition : expression ? There's no "then" meaning to
it.

rue

unread,
Oct 13, 2005, 6:07:32 PM10/13/05
to
Aargh, no! :)

Anything but adding syntax. I bet that someone somewhere can either
coax YACC to Do The Right Thing or then re-implement the whole thing
in ANTLR or something. We just need to find that person.

And there we have it, noble knights. Our quest is for the Magical
Parser.
Prepare your mounts, we ride at dawn.

David A. Black

unread,
Oct 13, 2005, 6:54:50 PM10/13/05
to
Hi --

That's one of the things I don't like about it. Just on a kind of
visceral level, { ... } conveys a much greater sense of a "closure".

Actually, if we must have -> then it would be better to just make it
look more like a method definition, but anonymous:

def x(a,b)
...
end

-> (a,b)
...
end

and just forget about the {}. ->(){} just requires too much visual
parsing and explaining.

Trans

unread,
Oct 13, 2005, 9:24:49 PM10/13/05
to

David A. Black wrote:

> That's one of the things I don't like about it. Just on a kind of
> visceral level, { ... } conveys a much greater sense of a "closure".

Yes, I felt that way as well. But I also sometimes feel like it's
(visually) lopsided.

each {|x| ... }

> Actually, if we must have -> then it would be better to just make it
> look more like a method definition, but anonymous:
>
> def x(a,b)
> ...
> end
>
> -> (a,b)
> ...
> end

Hmmm, can that be done? That must cause possible ambiguities or why
would we not be using {(x,y)...} already? But then again I know we can
do

def foo(x) do stuff ; end

So I'm not sure.

Matz had also suggested the possibility of ;; for end. Which with your
concept would give.

each -> (x) puts x ;;

I think even uglier. Let's try this:

each -> (x) puts x <-

Oh, yea now were getting somewhere. How about we sub '{' and '}' for
'->' and '<-'? Good idea? ;)

I'm being silly but the point is that you indrectly raise the fair
question of why not

{ (a,b) ... }

> and just forget about the {}. ->(){} just requires too much visual
> parsing and explaining.

->(){} ?

Oh, you mean empty-block? :)

T.

ES

unread,
Oct 13, 2005, 11:01:19 PM10/13/05
to
Trans wrote:
> David A. Black wrote:
>
>
>>That's one of the things I don't like about it. Just on a kind of
>>visceral level, { ... } conveys a much greater sense of a "closure".
>
>
> Yes, I felt that way as well. But I also sometimes feel like it's
> (visually) lopsided.
>
> each {|x| ... }
>
>
>>Actually, if we must have -> then it would be better to just make it
>>look more like a method definition, but anonymous:
>>
>> def x(a,b)
>> ...
>> end
>>
>> -> (a,b)
>> ...
>> end
>
>
> Hmmm, can that be done? That must cause possible ambiguities or why
> would we not be using {(x,y)...} already? But then again I know we can
> do
>
> def foo(x) do stuff ; end
>
> So I'm not sure.
>
> Matz had also suggested the possibility of ;; for end. Which with your
> concept would give.

I seem to recall this suggestion was presented on 2005.04.01.

> each -> (x) puts x ;;
>
> I think even uglier. Let's try this:
>
> each -> (x) puts x <-
>
> Oh, yea now were getting somewhere. How about we sub '{' and '}' for
> '->' and '<-'? Good idea? ;)
>
> I'm being silly but the point is that you indrectly raise the fair
> question of why not
>
> { (a,b) ... }
>
>
>>and just forget about the {}. ->(){} just requires too much visual
>>parsing and explaining.
>
>
> ->(){} ?
>
> Oh, you mean empty-block? :)

No syntax! :)

Damn, we could have *all* learned ANTLR by now.

> T.

E

Christian Neukirchen

unread,
Oct 14, 2005, 8:57:25 AM10/14/05
to
"David A. Black" <dbl...@wobblini.net> writes:

Read the : as "do". When x is one, do... For every item of the
collection, do...

I think the :(){} stuff is the nicest looking approach as of now, but
I wouldn't use it when ordinary {||} is enough.

> David
--
Christian Neukirchen <chneuk...@gmail.com> http://chneukirchen.org


David A. Black

unread,
Oct 14, 2005, 9:16:30 AM10/14/05
to
Hi --

On Fri, 14 Oct 2005, Christian Neukirchen wrote:

> "David A. Black" <dbl...@wobblini.net> writes:
>
>> Hi --
>>
>> On Fri, 14 Oct 2005, Gyoung-Yoon Noh wrote:
>>
>>> +1
>>>
>>> collection.each : (foo="bar") { puts foo }
>>>
>>> It looks like 'when condition : expression' branch in
>>> 'case' statement.
>>
>> But why would you want a method call and argument list and block to
>> look like when condition : expression ? There's no "then" meaning to
>> it.
>
> Read the : as "do". When x is one, do... For every item of the
> collection, do...

But it's such a stretch to look at it that way (and it's not the same
"do" as the usual "do").

> I think the :(){} stuff is the nicest looking approach as of now, but
> I wouldn't use it when ordinary {||} is enough.

As I said previously, I think that if there's a block syntax with (),
it should *not* have {}. There's simply no reason for {} at that
point, and all it does is make the () feel like it's in the wrong
place.

I still just can't imagine having two ways to do all of this -- trying
to explain it, reconcile it with other syntax, etc. It's bad enough
that people debate things like using empty parens on method calls, or
whether to omit "return".... The thought of people having to learn
two block syntaxes, and choosing between them, and debating it (which
*will* happen, at great length), all because of the stupid pipe
character.... oy vey.

Oh well, back to RubyConf preparation :-)

It is loading more messages.
0 new messages