123

I'm really confused about the difference between each.with_index and each_with_index. They have different types but seem to be identical in practice.

Yu Hao
  • 119,891
  • 44
  • 235
  • 294
Stan
  • 2,010
  • 3
  • 16
  • 12

2 Answers2

216

The with_index method takes an optional parameter to offset the starting index. each_with_index does the same thing, but has no optional starting index.

For example:

[:foo, :bar, :baz].each.with_index(2) do |value, index|
    puts "#{index}: #{value}"
end

[:foo, :bar, :baz].each_with_index do |value, index|
    puts "#{index}: #{value}"
end

Outputs:

2: foo
3: bar
4: baz

0: foo
1: bar
2: baz
blacktide
  • 10,654
  • 8
  • 33
  • 53
57

each_with_index was introduced into Ruby earlier. with_index was introduced later:

  1. to allow wider usage with various enumerators.
  2. to allow index to start from a number other than 0.

Today, using with_index would be better from the point of view of generality and readability, but from the point of view of speeding up the code, each_with_index runs slightly faster than each.with_index.

When you feel that a single method can be easily expressed by straightforward chaining of a few methods, it is usually the case that the single method is faster than the chain. As for another example of this, reverse_each runs faster than reverse.each. These methods have reason to exist.

the Tin Man
  • 158,662
  • 42
  • 215
  • 303
sawa
  • 165,429
  • 45
  • 277
  • 381