Ruby:Proc#call与收益率 [英] Ruby: Proc#call vs yield
问题描述
以下两个在Ruby中thrice
方法的实现之间的行为区别是什么?
What are the behavioural differences between the following two implementations in Ruby of the thrice
method?
module WithYield
def self.thrice
3.times { yield } # yield to the implicit block argument
end
end
module WithProcCall
def self.thrice(&block) # & converts implicit block to an explicit, named Proc
3.times { block.call } # invoke Proc#call
end
end
WithYield::thrice { puts "Hello world" }
WithProcCall::thrice { puts "Hello world" }
通过行为差异",我包括错误处理,性能,工具支持等.
By "behavioural differences" I include error handling, performance, tool support, etc.
推荐答案
我认为第一个实际上是另一个的语法糖.换句话说,没有行为上的差异.
I think the first one is actually a syntactic sugar of the other. In other words there is no behavioural difference.
第二种形式允许的是将块保存"在变量中.然后可以在其他时间点调用该块-回调.
What the second form allows though is to "save" the block in a variable. Then the block can be called at some other point in time - callback.
好的.这次我去做了一个快速基准测试:
Ok. This time I went and did a quick benchmark:
require 'benchmark'
class A
def test
10.times do
yield
end
end
end
class B
def test(&block)
10.times do
block.call
end
end
end
Benchmark.bm do |b|
b.report do
a = A.new
10000.times do
a.test{ 1 + 1 }
end
end
b.report do
a = B.new
10000.times do
a.test{ 1 + 1 }
end
end
b.report do
a = A.new
100000.times do
a.test{ 1 + 1 }
end
end
b.report do
a = B.new
100000.times do
a.test{ 1 + 1 }
end
end
end
结果很有趣:
user system total real
0.090000 0.040000 0.130000 ( 0.141529)
0.180000 0.060000 0.240000 ( 0.234289)
0.950000 0.370000 1.320000 ( 1.359902)
1.810000 0.570000 2.380000 ( 2.430991)
这表明使用 block.call 的速度几乎比使用收益的速度快2倍.
This shows that using block.call is almost 2x slower than using yield.
这篇关于Ruby:Proc#call与收益率的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!