2008-11-25 129 views
1

我經常聽到過Ruby的注射方法批評爲「慢」。由於我比較喜歡的功能,並看到其他語言的等價物,我很好奇,如果它只是Ruby的是很慢,或者如果它本身是做事情慢的方式(應避免非例如方法實施小集合)?#inject和緩慢

回答

3

inject就像fold,並且可以在其他語言非常有效的,特別是fold_left,因爲它是尾遞歸。

2

這主要是一個執行問題,但是這給你的比較好主意:

$ ruby -v 
ruby 1.8.7 (2008-08-11 patchlevel 72) [i486-linux] 
$ ruby exp/each_v_inject.rb 
Rehearsal ----------------------------------------------------- 
loop    0.000000 0.000000 0.000000 ( 0.000178) 
fixnums each  0.790000 0.280000 1.070000 ( 1.078589) 
fixnums each add 1.010000 0.290000 1.300000 ( 1.297733) 
Enumerable#inject 1.900000 0.430000 2.330000 ( 2.330083) 
-------------------------------------------- total: 4.700000sec 

         user  system  total  real 
loop    0.000000 0.000000 0.000000 ( 0.000178) 
fixnums each  0.760000 0.300000 1.060000 ( 1.079252) 
fixnums each add 1.030000 0.280000 1.310000 ( 1.305888) 
Enumerable#inject 1.850000 0.490000 2.340000 ( 2.340341) 

EXP/each_v_inject.rb

require 'benchmark' 

total = (ENV['TOTAL'] || 1_000).to_i 
fixnums = Array.new(total) {|x| x} 

Benchmark.bmbm do |x| 
    x.report("loop") do 
    total.times { } 
    end 

    x.report("fixnums each") do 
    total.times do |i| 
     fixnums.each {|x| x} 
    end 
    end 

    x.report("fixnums each add") do 
    total.times do |i| 
     v = 0 
     fixnums.each {|x| v += x} 
    end 
    end  

    x.report("Enumerable#inject") do 
    total.times do |i| 
     fixnums.inject(0) {|a,x| a + x } 
    end 
    end 
end 

所以是的,它是緩慢的,但隨着科技進步出現在實施過程中,它應該成爲一個非問題。沒有什麼固有的關於它在做什麼,需要它要慢一些。

0

each_with_object可能比inject更快,如果你是變異現有的對象,而不是建立在每個塊的新對象。