Hi,

2008/8/6 David A. Black <dblack / rubypal.com>:
> I'd rather have an enumerator that already knows both the method it
> represents and the block it's supposed to use. I guess I got used to
> it when we had:
>
>  e = array.enum_for(:map, &block)
>
> and I never understood why that was removed. I think it's someone
> else's "least surprise" :-)

First of all,

  e = array.enum_for(:map)
  p e.each(&block)

is equivalent to:

  p e.map(&block)

Then,

  e = array.enum_for(:map, &block1)
  p e.each(&block2)

is equivalent to:

  p e.map(&block2)
  # block1 is ignored for the same reason that Kernel#print ignores blocks.

I would be surpised if it's equivalent to:

  p e.map(&block1).each(&block2)

or

  p e.map(&block1).map(&block2)

But you want this behaviour, don't you?

Speaking about implementation, Enumerable#map is impletented as follows:

module Enumerable
  # actually implemented in C
  def map
    result = []
    each do |i|
      result << yield(i)
    end
    return result
  end
end

How do you convert it into Enumerator as you think automatically?  I can't
think of any implementation other than the following example:

module Enumerable
  def my_enum_for(method, &block)
    return send(method, &block).enum_for(:each)
  end
end

But it's not efficient, and I think it's necessary for an efficent
implementation
to modify Enumerable#map itself.

-- 
Shugo Maeda