2010-08-31 65 views
0

我有這樣多線程紅寶石

myhash.each_value{|subhash| 
    (subhash['key]'.each {|subsubhash| 

    statement that modifies the subsubhash and takes about 0.07 s to execute 
    }) 
    } 

這個循環運行100+次,不用說一個代碼片段減慢我的應用程序極大(大約7秒鐘,運行這個循環)。

任何關於如何使這個更快的指針?我無法控制真正的昂貴聲明。有沒有一種方法可以在循環中使用多線程,以便可以並行執行語句?

回答

0
threads = [] 
myhash.each_value{ |subhash| 
    threads << Thread.start do 
    subhash['key'].each { |subsubhash| 
    threads << Thread.start do 
     statement that modifies the subsubhash and takes about 0.07 s to execute 
    end 
    } 
    end 
} 
threads.each { |t| t.join } 

請注意,MRI 1.8.x不使用真正的線程,而是使用真正的線程,而不是真正的操作系統線程。但是,如果您使用JRuby,則可能會看到性能提升,因爲它支持真正的線程。

+0

您需要的Thread.join在那裏的某個地方,以確保所有的線程完成。你還需要擔心這是線程安全的,也就是說,「修改subhash的語句......」在其計算中使用任何其他散列鍵? – 2010-08-31 17:52:34

+0

我提到,他需要做的,我最初的職位的加入,但我添加的代碼在那裏只爲你:P。至於線程safeness,我想這是到OP決定耐候這是一個問題或沒有,因爲我不能用他的僞告訴。 – Mahmoud 2010-08-31 18:17:32

+0

謝謝大家的建議。我想這一點,像所有的你說的,我也沒有真正得到離譜了吧。責備口譯員。 – rubyer 2010-09-08 15:22:29

0

您可以在單獨的線程中運行每個subhash處理循環,但是否會導致性能提升可能取決於(1)您正在使用的Ruby解釋器或(2)最內部塊是否爲IO綁定或計算限制的。

#1的原因是一些Ruby解釋器(例如CRuby/MRI 1.8)使用green threads,即使在多核機器上,它通常不會受益於任何實際的並行處理。但是,YARV和JRuby都使用本地操作系統線程(因爲JVM使用本地線程,所以即使是1.8版本的JRuby也是如此),所以如果您可以專門針對這些解釋器,那麼您可能會看到改進。

原因#2是,如果最裏面塊IO綁定,然後因爲大多數操作系統做調度線程的一個好工作圍繞阻塞IO調用甚至綠色基於線程的解釋可能會提高性能。如果塊是嚴格計算綁定的,那麼只有基於本地線程的解釋器可能會顯示使用多線程的性能提升。