【发布时间】:2014-04-20 01:46:01
【问题描述】:
Procs 和 lambdas differ 与方法范围和 return 关键字的效果有关。我对它们之间的性能差异很感兴趣。我写了一个测试,如下图:
def time(&block)
start = Time.now
block.call
p "that took #{Time.now - start}"
end
def test(proc)
time{(0..10000000).each{|n| proc.call(n)}}
end
def test_block(&block)
time{(0..10000000).each{|n| block.call(n)}}
end
def method_test
time{(1..10000000).each{|n| my_method(n)}}
end
proc1 = Proc.new{|x| x*x}
proc2 = proc{|x| x*x}
lam1 = lambda{|x| x*x}
lam2 = ->x{x*x}
def my_method(x)
x*x
end
test(proc1)
test(proc2)
test(lam1)
test(lam2)
test_block{|x| x*x}
test(method(:my_method))
method_test
这段代码的结果如下所示。
"that took 0.988388739"
"that took 0.963193172"
"that took 0.943111226"
"that took 0.950506263"
"that took 0.960760843"
"that took 1.090146951"
"that took 0.644500627"
method(:my_method) 是最慢的,这是因为它会为循环中的每次迭代检查查找表。
同样的,另一个测试如下:
def test2(&block)
time{(0..1000000).each{block.call}}
end
test2{Proc.new{|x| x*x}}
test2{proc{|x| x*x}}
test2{lambda{|x| x*x}}
test2{->(x){x*x}}
返回这个结果:
"that took 0.415290453"
"that took 0.378787963"
"that took 0.3888118"
"that took 0.391414639"
Proc.new 是最慢的创建方法,这是因为我们有创建整个对象来包装我们的 proc 的开销。
我断言无论它们的创建方法如何,proc 和 lambda 的执行时间都是相同的。
- 为什么普通方法调用比 procs 和 lambda 快得多(减少 1/3 时间)?
- 人们是否认为这可能会随着不同的块功能等而改变?
- 在不同方法之间进行选择是否还有其他(基于性能的)原因?
【问题讨论】:
-
没有没有个基于性能的理由来选择它们。它们是不同的东西,为不同的目的而构建。试图比较它们的性能就像比较赛车和拖车的速度。
-
@LoganSerman 谢谢,很高兴知道。
-
@meagar 我会提出异议,如果我不将我的 proc 或 lambda 放入一个方法中并且从不调用 return 或 break (这对我来说很常见,因为我尝试编写了许多我的功能风格的脚本并使用我们拥有的美妙的新惰性迭代器)然后它们在功能上是等效的,(不是吗?)在这种情况下我应该用什么来选择它们,我目前使用 stabby lambda 因为它是最快的打字,但我想做出明智的决定。在我刚才提出的情况下,它们有什么不同吗?
标签: ruby performance lambda proc