Vikram Singh Jadon Vikram Singh Jadon - 1 year ago 82
Ruby Question

Ruby - working of "yield" in Iterator each

A method can invoke an associated block of code one or more times using the Ruby yield statement. we can also pass values to the block by giving parameters to yield in vertical bars (|). Just like I have done below.

1 def print_name
2 puts "Hello "
3 yield "Vikram"
4 end
6 animals = %w( ant bee cat dog elk )
7 animals.each {|animal| puts animal }
8 animals.each
10 print_name {|name| puts name}
11 print_name

In my code line number 11 is giving an error that :

`print_name': no block given (yield) (LocalJumpError)

This means we cannot use yield in a method without passing a block of code while calling the method.

My question is that, how in my above code "animals.each" (refer line 8) is working without giving any error, if there is a "yield" statement present inside "each" method of ruby?

If it is not present then

animals.each {|animal| puts animal }

this should not have worked.


Ruby allows you to check whether a block was passed to the current method by using Kernel#block_given?. Array#each, as the documentation says, returns an enumerator if no block is given (which is checked using block_given?).

Unlike each, your print_name method tries to yield regardless of whether a block was given, leading to the error on line 11.