Question about passing an array iterator instance to a block

I was always under assumption that the block accepts the return value
of the iterator as the argument to the block, but look at this:

Array.new(500) do | i |
puts i
end

I expect i to be an array instance with 500 indexes all will nil
values. However, what it returns is indeed an array with 500 indexes
all with nil values BUT before it returns that array instance, the
block appears to execute 500 times passing an actual integer value
into the block incrementing by 1 each time. I dont understand why this
is happening.

thanks for response

On 25.02.2012, at 23:41, John M. wrote:

all with nil values BUT before it returns that array instance, the
block appears to execute 500 times passing an actual integer value
into the block incrementing by 1 each time. I dont understand why this
is happening.

Because ‘puts()’ always return nil. It just generates STDOUT output.

thanks for response but that was just an example and not really what
my question was about.

Perhaps this is a better example:

Array.new(10) do |id|
?> “’#{(id + 1).to_s.rjust(2,“0”)}’”

end
=> ["‘01’", “‘02’”, “‘03’”, “‘04’”, “‘05’”, “‘06’”, “‘07’”, “‘08’”,
“‘09’”, “‘10’”]

Why is “id” not the array instance. It obviously is an integer.
Otherwise this would have failed with (id +1).

On 26.02.2012, at 0:07, John M. wrote:

Why is “id” not the array instance. It obviously is an integer.
Otherwise this would have failed with (id +1).

I don’t understand Why are you expecting an Array??

new(size=0, obj=nil)click to toggle source
new(array)
new(size) {|index| block }
Returns a new array. In the first form, the new array is empty. In the
second it is created with sizecopies of obj (that is, size references to
the same obj). The third form creates a copy of the array passed as a
parameter (the array is generated by calling to_ary on the parameter).
In the last form, an array of the given size is created. Each element in
this array is calculated by passing the elements index to the given
block and storing the return value.

There must be code inside like that:

if block_given?
yield index
end

You know what your completely right. The block only will take what the
yield method returns to it. So apparently when instantiating an array
with that first argument setting a size limit for array, the
constructor contains a yield method which yields each iteration of
that size limit. And then the return value is passed back to the
resutlt of the yield and that value is then idnexed into the array
until the size limit has been reached.

On Sat, Feb 25, 2012 at 15:15, Valery K. [email protected] wrote:

There must be code inside like that:

if block_given?
yield index
end

That wouldn’t do the setting of the values in the array. Maybe:

if block_given?
size.times { |index| self << yield index }
end

or, if it already needs to loop over it to initialize the slot:

size.times do |index|

do other initialization

self << yield(index) if block_given?
end

-Dave


Dave A.: Available Cleared Ruby on Rails Freelancer
(NoVa/DC/Remote) – see www.DaveAronson.com, and blogs at
www.Codosaur.us, www.Dare2XL.com, www.RecruitingRants.com