Search code examples
rubycar-analogy

Ruby: difference between @cars.each do |car| and for car in @cars do


(Sorry for the newbie question.) In Ruby, what is the difference between the loops:

@cars.each do |car| 

and

for car in @cars do

?

is there a difference in efficiency, or why do we need two (or more) ways to express the same thing? The second way seems more elegant/natural to me, but I may be missing some crucial observation, why the first may be the better choice.


Solution

  • More people use the @cars.each notation because that generalizes to other methods (like #inject, #each_with_index, #map, etc, as well as non-iterator callbacks).

    for/in is mainly just syntactic sugar for #each. The main difference in how the two work is in variable scoping:

    irb> @cars = %w{ ford chevy honda toyota }
    #=> ["ford", "chevy", "honda", "toyota"]
    irb> @cars.each { |car| puts car }
    ford
    chevy
    honda
    toyota
    #=> ["ford", "chevy", "honda", "toyota"]
    irb> car
    NameError: undefined local variable or method `car` for #<Object:0x399770 @cars=["ford", "chevy", "honda", "toyota"]>
            from (irb):3
            from /usr/local/bin/irb:12:in `<main>`
    irb> for car in @cars
         puts car.reverse
         end
    drof
    yvehc
    adnoh
    atoyot
    #=> ["ford", "chevy", "honda", "toyota"]
    irb> car
    #=> "toyota"
    

    for/in leaves the iterator variable in scope afterwards, while #each doesn't.

    Personally, I never use ruby's for/in syntax.