parallel method return value

L

Louis-Philippe

[Note: parts of this message were removed to make it a legal post.]

Hi all,
this is assignment behaviour:
a,b = 1,2,3 => [1, 2, 3]
a => 1
b
=> 2

and with a method:
def a_method
return 1, 2, 3
end => nil
a,b = a_method => [1, 2, 3]
a => 1
b
=> 2

If I want only one lvalue, is this:
a, = 1, 2, 3 => [1, 2, 3]
a
=> 1
the only way to get it?

I would have liked for the return behaviour to be set on the right side,
to allow method invocation like:
to return:
1

instead of
1
2
3

Thanks all!

L-P
 
M

Matthew Moss

and with a method:
def a_method
return 1, 2, 3
end => nil
a,b = a_method => [1, 2, 3]
a => 1
b
=> 2

If I want only one lvalue, is this:
a, = 1, 2, 3 => [1, 2, 3]
a
=> 1
the only way to get it?

I would have liked for the return behaviour to be set on the right
side,
to allow method invocation like:
to return:
1

instead of
1
2
3


So... uh, why wouldn't you just return one value? That is:

def a_method
return 1
end

???

Perhaps, if it's an array you have, then just use method #first:

def a_method
return some_array.first
end
 
B

Brian Candler

Louis-Philippe said:
and with a method:

This behaves identically to

return [1, 2, 3]

That is, a single array object is returned. AFAIK, methods always return
exactly one value.
If I want only one lvalue, is this:
a, = 1, 2, 3 => [1, 2, 3]
a
=> 1
the only way to get it?

a = a_method

is saying "assign whatever object is returned from a_method to a", and
if that's an array, then an array is what you get.

You can use the multiple-assignment syntax to drop the rest, or other
Array operations like

a = a_method[0]

a = a_method.first
I would have liked for the return behaviour to be set on the right side,
to allow method invocation like:

to return:
1

instead of
1
2
3

If a function returns an array, that's what I want to see; I wouldn't
want it to be arbitarily munged.
 
L

Louis-Philippe

[Note: parts of this message were removed to make it a legal post.]

Hi guys,

Thanks for your answer,I get your points...
but in this case, what I really want to do is have the method return the
right number of values for the corresponding quantity of lvalues presented
to it, to make it context sensitive you know, so I can have, for example, a
boolean first return value when it is called with one lvalue and a boolean
plus a string when called with two rvalue. The assignment operator does it,
so I would have expected the same behaviour to also work with a method.

right now my options are:

a, = a_method

or

a = a_method[0]

both ways still involve to ask for only one to return. What I am looking
for, if it exist, is for the method to automatically detect context and act
from it like the = operator. I find how the assignment operator implements
this is very elegant, and am crave it for methods!!
But... those are probably the only ways to do it, because as Brian
said "methods
always return exactly one value", and that is what I had previously
concluded from experimentation and reading the documentation.
Anybody can prove this wrong? (please!!)

thanks!

L-P

2008/12/12 Brian Candler said:
Louis-Philippe said:
and with a method:

This behaves identically to

return [1, 2, 3]

That is, a single array object is returned. AFAIK, methods always return
exactly one value.
If I want only one lvalue, is this:
a, = 1, 2, 3 => [1, 2, 3]
a
=> 1
the only way to get it?

a = a_method

is saying "assign whatever object is returned from a_method to a", and
if that's an array, then an array is what you get.

You can use the multiple-assignment syntax to drop the rest, or other
Array operations like

a = a_method[0]

a = a_method.first
I would have liked for the return behaviour to be set on the right side,
to allow method invocation like:

to return:
1

instead of
1
2
3

If a function returns an array, that's what I want to see; I wouldn't
want it to be arbitarily munged.
 
M

Matthew Moss

Hi guys,

Thanks for your answer,I get your points...
but in this case, what I really want to do is have the method return
the
right number of values for the corresponding quantity of lvalues
presented
to it, to make it context sensitive you know, so I can have, for
example, a
boolean first return value when it is called with one lvalue and a
boolean
plus a string when called with two rvalue. The assignment operator
does it,
so I would have expected the same behaviour to also work with a
method.

But as was pointed out, methods _always_ return one value, even if it
appears to return multiple values. They are lumped together into one
array.
right now my options are:

a, = a_method

or

a = a_method[0]

both ways still involve to ask for only one to return. What I am
looking
for, if it exist, is for the method to automatically detect context
and act
from it like the = operator. I find how the assignment operator
implements
this is very elegant, and am crave it for methods!!

There isn't any way for the method call to recognize the context in
which it is being called. You'd have to pass an argument, such as the
"number of return values" to return.

a, b = a_method(2)
a = a_method(1)

Which seems pointless, when you can instead do what you've already
identified as the proper technique:

a, = a_method
a, b = a_method
a, b, c = a_method
# etc.
Anybody can prove this wrong? (please!!)

No, because what was provided before wasn't wrong.
 
L

Louis-Philippe

[Note: parts of this message were removed to make it a legal post.]

Thanks Matthew,

"No, because what was provided before wasn't wrong."

Yeah... I believe you, but would really like it to be else!

L-P

2008/12/12 Matthew Moss said:
On Dec 12, 2008, at 1:25 PM, Louis-Philippe wrote:

Hi guys,
Thanks for your answer,I get your points...
but in this case, what I really want to do is have the method return the
right number of values for the corresponding quantity of lvalues presented
to it, to make it context sensitive you know, so I can have, for example,
a
boolean first return value when it is called with one lvalue and a boolean
plus a string when called with two rvalue. The assignment operator does
it,
so I would have expected the same behaviour to also work with a method.

But as was pointed out, methods _always_ return one value, even if it
appears to return multiple values. They are lumped together into one array.

right now my options are:
a, = a_method

or

a = a_method[0]

both ways still involve to ask for only one to return. What I am looking
for, if it exist, is for the method to automatically detect context and
act
from it like the = operator. I find how the assignment operator
implements
this is very elegant, and am crave it for methods!!

There isn't any way for the method call to recognize the context in which
it is being called. You'd have to pass an argument, such as the "number of
return values" to return.

a, b = a_method(2)
a = a_method(1)

Which seems pointless, when you can instead do what you've already
identified as the proper technique:

a, = a_method
a, b = a_method
a, b, c = a_method
# etc.

Anybody can prove this wrong? (please!!)
No, because what was provided before wasn't wrong.
 
M

Matthew Moss

Thanks Matthew,

"No, because what was provided before wasn't wrong."

Yeah... I believe you, but would really like it to be else!


Think of it this way...

def foo
return 1, 2, 3
end

a = foo

Now, you want a to be 1, but Ruby would need the power to read minds
to accommodate that. See, because if I do the same, I want a to be [1,
2, 3]. How is foo supposed to figure that out? Or why should your want
be more/less preferable than my want?

Simply, the interpreter can't know. There has to be some syntax or
something that gives foo, or the assignment to a, that key information.

Telling foo would be passing an arg:

def foo(nargs)
return [1, 2, 3][0...nargs]
end

a = foo(1)

Any of the other examples come after foo is done, so:

def foo
return 1, 2, 3
end

a, = foo
a = foo[0]
a = foo.first

All three of those do the same... assign 1 to a. The latter two
request specifically the first item, while the first does parallel
assignment (of array components to particular variables... in this
case, only a). Since you seem interested in parallel assignment to a
variable number of variables, the first seems appropriate. Granted,
forgetting the comma might be easy, but there's no way for foo to know
that you want a = foo to return 1 and that someone else that does a =
foo wants [1, 2, 3].
 
E

Einar Magnús Boson

Thanks Matthew,

"No, because what was provided before wasn't wrong."

Yeah... I believe you, but would really like it to be else!


Think of it this way...

def foo
return 1, 2, 3
end

a = foo

Now, you want a to be 1, but Ruby would need the power to read minds
to accommodate that. See, because if I do the same, I want a to be
[1, 2, 3]. How is foo supposed to figure that out? Or why should
your want be more/less preferable than my want?

Simply, the interpreter can't know. There has to be some syntax or
something that gives foo, or the assignment to a, that key
information.

Telling foo would be passing an arg:

def foo(nargs)
return [1, 2, 3][0...nargs]
end

a = foo(1)

Any of the other examples come after foo is done, so:

def foo
return 1, 2, 3
end

a, = foo
a = foo[0]
a = foo.first

All three of those do the same... assign 1 to a. The latter two
request specifically the first item, while the first does parallel
assignment (of array components to particular variables... in this
case, only a). Since you seem interested in parallel assignment to a
variable number of variables, the first seems appropriate. Granted,
forgetting the comma might be easy, but there's no way for foo to
know that you want a = foo to return 1 and that someone else that
does a = foo wants [1, 2, 3].


He isn't asking ruby to read minds, he is asking about overloading on
expected number of return values like e.g. matlab does. But it is like
everyone is saying, Ruby doesn't do that, sorry.

einarmagnus
 
E

Ezra Zygmuntowicz

Hi~

Thanks Matthew,

"No, because what was provided before wasn't wrong."

Yeah... I believe you, but would really like it to be else!


Think of it this way...

def foo
return 1, 2, 3
end

a = foo

Now, you want a to be 1, but Ruby would need the power to read minds
to accommodate that. See, because if I do the same, I want a to be
[1, 2, 3]. How is foo supposed to figure that out? Or why should
your want be more/less preferable than my want?

Simply, the interpreter can't know. There has to be some syntax or
something that gives foo, or the assignment to a, that key
information.

Telling foo would be passing an arg:

def foo(nargs)
return [1, 2, 3][0...nargs]
end

a = foo(1)

Any of the other examples come after foo is done, so:

def foo
return 1, 2, 3
end

a, = foo
a = foo[0]
a = foo.first

All three of those do the same... assign 1 to a. The latter two
request specifically the first item, while the first does parallel
assignment (of array components to particular variables... in this
case, only a). Since you seem interested in parallel assignment to a
variable number of variables, the first seems appropriate. Granted,
forgetting the comma might be easy, but there's no way for foo to
know that you want a = foo to return 1 and that someone else that
does a = foo wants [1, 2, 3].



you can use the masign commas to get sort of what you want:

irb(main):001:0> def foo
irb(main):002:1> return 1,2,3
irb(main):003:1> end
=> nil
irb(main):004:0> a, = foo
=> [1, 2, 3]
irb(main):005:0> a
=> 1


Cheers-

Ezra Zygmuntowicz
(e-mail address removed)
 
M

Matthew Moss

a, = foo
a = foo[0]
a = foo.first

All three of those do the same... assign 1 to a. The latter two
request specifically the first item, while the first does parallel
assignment (of array components to particular variables... in this
case, only a). Since you seem interested in parallel assignment to
a variable number of variables, the first seems appropriate.
Granted, forgetting the comma might be easy, but there's no way for
foo to know that you want a = foo to return 1 and that someone else
that does a = foo wants [1, 2, 3].

you can use the masign commas to get sort of what you want:

irb(main):001:0> def foo
irb(main):002:1> return 1,2,3
irb(main):003:1> end
=> nil
irb(main):004:0> a, = foo
=> [1, 2, 3]
irb(main):005:0> a
=> 1


You mean like my first example above? :D
 
L

Louis-Philippe

[Note: parts of this message were removed to make it a legal post.]
Now, you want a to be 1, but Ruby would need the power to read minds to
accommodate that. See, because if I do the same, I want a to be [1, 2, 3].
How is foo supposed to figure that out? Or why should your want be more/less
preferable than my want?

You're totally right Matthew, I was twisted into thinking assignment would
do it for one lvalue with multiple rvalues...
Its probably a crazy idea, and who am I to have idea about language design
without any means to implement them...
but anyway, here's my thought (its this one that got me twisted).
Since the splat operator does nothing when preceding a rvalue of only one
array, like in:

a = *[1,2,3] # => a = [1,2,3]
a = [1,2,3] # => a = [1,2,3]

a,b = *[1,2,3] # => a = 1, b = 2
a,b = [1,2,3] # => a = 1, b = 2

It would be in line with its normal use, to make all array items absolutely
separate,
allowing for the impossible: a = *[1,2,3] # => a = 1 (I know, this is
not working code, but thats how my head go previously twisted).
... I was just thinking out loud, I believe there is certainly a really good
logic to explain why this fabulous language doesn't already implement this
feature, it surely won't stop me in my unconditional ruby love ;)

L-P
 
E

Ezra Zygmuntowicz

a, = foo
a = foo[0]
a = foo.first

All three of those do the same... assign 1 to a. The latter two
request specifically the first item, while the first does parallel
assignment (of array components to particular variables... in this
case, only a). Since you seem interested in parallel assignment to
a variable number of variables, the first seems appropriate.
Granted, forgetting the comma might be easy, but there's no way
for foo to know that you want a = foo to return 1 and that someone
else that does a = foo wants [1, 2, 3].

you can use the masign commas to get sort of what you want:

irb(main):001:0> def foo
irb(main):002:1> return 1,2,3
irb(main):003:1> end
=> nil
irb(main):004:0> a, = foo
=> [1, 2, 3]
irb(main):005:0> a
=> 1


You mean like my first example above? :D

Yes exactly like that! /me wanders off to get some glasses...

Ezra
 
M

Matthew Moss

Now, you want a to be 1, but Ruby would need the power to read
minds to
accommodate that. See, because if I do the same, I want a to be [1,
2, 3].
How is foo supposed to figure that out? Or why should your want be
more/less
preferable than my want?

You're totally right Matthew, I was twisted into thinking assignment
would
do it for one lvalue with multiple rvalues...
Its probably a crazy idea, and who am I to have idea about language
design
without any means to implement them...

Well, I shouldn't have said, "No, completely impossible." Other
languages may do what you want. As far as Ruby goes, the options I see
are:

1. Deal with it.
2. Change design/spec of Ruby to return multiple values instead of one
array. (Serious work and impact.)
3. Have some sort of macro mechanism? (IE, where the call to foo would
be inlined... perhaps then allowing parallel assignment).
4. Support something like a = *[1, 2, 3] to mean a, = 1, 2, 3.
(Umm... hmm... dunno about that.)
5. Return a proxy? (This might not be any different from current
situation.)
6. Lambda/procs?
7. Make a a proxy/class/wrapper that does what you want.


My guess is that #1 is current situation, #2 and #4 won't happen, #3
I've no idea, #5 is no different than #1, and #6-7 I'd have to spend
some time thinking about. Maybe others have ideas on those.
 
T

Todd Benson

Now, you want a to be 1, but Ruby would need the power to read minds to
accommodate that. See, because if I do the same, I want a to be [1, 2, 3].
How is foo supposed to figure that out? Or why should your want be more/less
preferable than my want?

You're totally right Matthew, I was twisted into thinking assignment would
do it for one lvalue with multiple rvalues...
Its probably a crazy idea, and who am I to have idea about language design
without any means to implement them...
but anyway, here's my thought (its this one that got me twisted).
Since the splat operator does nothing when preceding a rvalue of only one
array, like in:

a = *[1,2,3] # => a = [1,2,3]
a = [1,2,3] # => a = [1,2,3]

a,b = *[1,2,3] # => a = 1, b = 2
a,b = [1,2,3] # => a = 1, b = 2

It would be in line with its normal use, to make all array items absolutely
separate,
allowing for the impossible: a = *[1,2,3] # => a = 1 (I know, this is
not working code, but thats how my head go previously twisted).
... I was just thinking out loud, I believe there is certainly a really good
logic to explain why this fabulous language doesn't already implement this
feature, it surely won't stop me in my unconditional ruby love ;)

L-P

Perhaps bring your interests to the ruby core list. I like it the way
it is. Ruby's parser assumes you require a single object unless the
left hand side is specified otherwise. I see no weirdness about this.

Todd
 
L

Louis-Philippe

[Note: parts of this message were removed to make it a legal post.]
Perhaps bring your interests to the ruby core list.


The way it works is already plentiful, I was just asking to know up to where
I could push it.
Maybe when I my knowledge of ruby gets a bit more maturity I'll be willing
to integrate the core list,
I don't feel I have enough perspective on the language right now to bring
anything to the ones which are into language design thinking.

Thanks,

L-P
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,982
Messages
2,570,189
Members
46,735
Latest member
HikmatRamazanov

Latest Threads

Top