classMyArrayattr_accessor:my_arrdefinitialize(my_arr)@my_arr=my_arrenddefmy_each(&my_block)foriin0..@my_arr.length-1my_block.call(@my_arr[i],i)endendenda=MyArray.new([1,2,3,4])a.my_each{|number,index|puts"number at #{index} has value #{number}"}
classMyArrayattr_accessor:my_arrdefinitialize(my_arr)@my_arr=my_arrenddefmy_yieldyieldendenda=MyArray.new([1,2,3,4])a.my_yield{puts"yield is also sexy!"}
请大家无视1,2,3,4, 上面的例子只会输出yield is also sexy!, 也就是说 a.my_yield 后面的所有内容都跑到 my_yield 中,替换了 yield,简单吧。
下面开始对其升级:
12345678910111213141516
classMyArrayattr_accessor:my_arrdefinitialize(my_arr)@my_arr=my_arrenddefmy_yieldyield(@my_arr)endenda=MyArray.new([1,2,3,4])a.my_yield{|my_tmp_arr|puts"yield with parameter!"my_tmp_arr.each{|number|putsnumber}}
multiply_lambda_proc=lambda{|x,y|x*y}# and we can call as a normal Procmultiply_lambda_proc.call(3,4)# return 12
其与 Proc 主要有两个不同点:
第一,lambda 会检查参数,而 Proc 不会。
12345678
multiply_lambda_proc=lambda{|x,y|x*y}multiply_proc=Proc.new{|x,y|x*y}multiply_lambda_proc.call(3,4,5)# ArgumentError: wrong number of arguments (3 for 2)multiply_proc(3,4,5)# return 12 as normal# This last command's error shows that Proc auto assigns missing argument with nilmultiply_proc(3)# TypeError: nil can't be coerced into Fixnum
第二,lambda 会返回它的调用函数,但 Proc 会结束它所位于的 function。
1234567891011121314
defreturn_from_procruby_proc=Proc.new{return"return from a Proc"}ruby_proc.callreturn"The function will NOT reach here because a Proc containing a return statement has been called"enddefreturn_from_lambdaruby_lambda=lambda{return"return from lambda"}ruby_lambda.callreturn"The function will reach here"endputsreturn_from_proc# display return from procputsreturn_from_lambda# display The function will reach here