2

ルビー ビルド スクリプトには、各プロジェクトを反復処理して msbuild を呼び出し、css/js の縮小などのさまざまな処理を実行するループがあります。

各ループ反復は他の反復とは独立しているため、並列化したいと思います。

どうすればいいですか?

私はもう試した:

myarray.each{|item|
    Thread.start {

        # do stuff

     }
}
puts "foo"

しかし、Ruby はすぐに終了するようです ("foo" が出力されます)。つまり、ループを実行し、スレッドのロードを開始しますが、 の後に何もないためeach、ruby は他のスレッドを強制終了して終了します :(

できることはわかっていますthread.joinが、ループ内でこれを行うと、並列ではなくなります。

私は何が欠けていますか?

私はhttp://peach.rubyforge.org/を認識していますが、それを使用すると、解決方法がわからない変数スコープの問題のように見えるあらゆる種類の奇妙な動作が発生します:(

編集:「foo」を置く前に、または少なくともメインのルビースレッドが終了する前に、すべての子スレッドが実行されるのを待つことができれば便利です。これは可能ですか?

ありがとう

4

3 に答える 3

6

すべてのスレッドを配列に格納し、join を呼び出して配列をループします。

threads = myarray.map do |item|
  Thread.start do
    # do stuff
  end
end
threads.each { |thread| thread.join }
puts "foo"
于 2012-04-19T09:10:38.597 に答える
2

ここでem-synchronyを使用してください:)。繊維がかわいいです。

require "em-synchrony"
require "em-synchrony/fiber_iterator"

# if you realy need to get a Fiber per each item
# in real life you could set concurrency to, for example, 10 and it could even improve performance
# it depends on amount of IO in your job
concurrency = myarray.size
EM.synchrony do
  EM::Synchrony::FiberIterator.new(myarray, concurrency).each do |url|
    # do some job here
  end
  EM.stop
end
于 2012-04-19T09:15:52.773 に答える
1

ruby スレッドはグリーン スレッドであるため、ネイティブに真の並列処理が行われないことを考慮してください。これがあなたの望むものなら、JRuby と Rubinius を参照することをお勧めします。

http://www.engineyard.com/blog/2011/concurrency-in-jruby/

于 2012-04-19T09:03:59.543 に答える