Object loops and what they return

> Consider these loops:
>
> <object>.<loop-method> { <code> }
>
> where loop method is each, each_with_index, upto, downto,
step,
> and probably others.
>
> Although it is not documented, all of these look to return
the
> original object (collection or int).

I think the return values are documented in ri for all of
these.

Enumerable says nothing about the return value or each.
Array.each says it returns an Array, but not what's in that
Array. Before testing, I was thinking it might be the same as
map/collect. The integer loops also say they return an
integer, but not what it is.

> With "each" returning nil, you can also see that many of
the
> derived loops in Enumerable become trival almost to where
you
> don't need them.

On the other hand, if you were to do this (looking for nil):

   obj = array.each {|e| break(e) if e.nil? }

and each returned nil, you wouldn't know whether you'd
succeeded or
not.

Then you do it another way. Differentiating between the
element nil in a collection and nil meaning nothing is a common
problem, I think. You have the same problem using find:

obj = array.find{|e| not e.kind_of?Integer }

If you were looking for the first non-integer in array and it
happened to be nil, you couldn't tell whether nil was that
object or there were no non-integers.

The various find and include? and any? and index methods are
probably
your best bet for this kind of operation.

In the particular code I was looking at, none of them worked (I
think I looked at all of them). I needed a different compare
(equal?) and in one case I wanted to go in reverse order.

Discover Yahoo!
Use Yahoo! to plan a weekend, have fun online and more. Check it out!
http://discover.yahoo.com/

Hi --

Consider these loops:

<object>.<loop-method> { <code> }

where loop method is each, each_with_index, upto, downto,

step,

and probably others.

Although it is not documented, all of these look to return

the

original object (collection or int).

I think the return values are documented in ri for all of
these.

Enumerable says nothing about the return value or each.

There's no Enumerable#each; you have to implement it :slight_smile:

Array.each says it returns an Array, but not what's in that
Array. Before testing, I was thinking it might be the same as
map/collect. The integer loops also say they return an
integer, but not what it is.

I think you're misreading the ri output. For example, in this:

    enum.each_with_index {|obj, i| block } -> enum

'enum' is a variable or object, and it is both the receiver of the
method and the return value. The 'enum' on the right is the same as
the 'enum' on the left. That documents the returning-receiver
behavior.

With "each" returning nil, you can also see that many of

the

derived loops in Enumerable become trival almost to where

you

don't need them.

On the other hand, if you were to do this (looking for nil):

   obj = array.each {|e| break(e) if e.nil? }

and each returned nil, you wouldn't know whether you'd
succeeded or
not.

Then you do it another way. Differentiating between the
element nil in a collection and nil meaning nothing is a common
problem, I think. You have the same problem using find:

obj = array.find{|e| not e.kind_of?Integer }

If you were looking for the first non-integer in array and it
happened to be nil, you couldn't tell whether nil was that
object or there were no non-integers.

That's true -- it's something one has to work around in various
places. I guess my feeling is that having each and friends return nil
won't cause that not to be the case, and that, given that double
checks and so on are sometimes needed, there's already a pretty full
tool set for doing them.

David

ยทยทยท

On Thu, 12 May 2005, Eric Mahurin wrote:

--
David A. Black
dblack@wobblini.net

Eric Mahurin wrote:

Enumerable says nothing about the return value or each.
Array.each says it returns an Array, but not what's in that
Array. Before testing, I was thinking it might be the same as
map/collect. The integer loops also say they return an
integer, but not what it is.

You seem to be not so much interested in whether or not people use this
feature, as instead convincing them that they shouldn't use them,
because you'd like to see the feature go away.

(Which is fine...expressing one's opinions and attempting to sway
others' it one fine use of the mailing list :slight_smile:

However, I fail to see as valid the argument that we should not be
using a feature just because the documentation is incomplete. Instead,
the documentation should be fixed.

There may certainly to be some side-effects of idiosyncracies of the
language implementation upon which one should not rely, but that
specific self return value of certain methods smells far more like an
intentional feature than a bug.

Your argument that they should return nil for consistency certainly has
some merit. I counter-argue that if you're always going to return the
same value from a method, returning the receiver is usually preferable
over returning nil.

I vote: don't take away my feature just because you don't like it, and
don't like that I use chaining across blocks which (to some) looks
ugly. :slight_smile: