2016-04-22 55 views
2

我是新來的光纖和EventMachine,並且最近才發現有關光纖,當我看到Ruby是否具有任何併發​​功能時,如go-lang。如何用Ruby的Fibers實現並行任務?

在使用光纖時,似乎並沒有太多的實例用於實際用例。

我還是設法找到這個:https://www.igvita.com/2009/05/13/fibers-cooperative-scheduling-in-ruby/(回從2009年!)

它具有以下代碼:

require 'eventmachine' 
require 'em-http' 
require 'fiber' 

def async_fetch(url) 
    f = Fiber.current 
    http = EventMachine::HttpRequest.new(url).get :timeout => 10 
    http.callback { f.resume(http) } 
    http.errback { f.resume(http) } 

    return Fiber.yield 
end 

EventMachine.run do 
    Fiber.new{ 
    puts "Setting up HTTP request #1" 
    data = async_fetch('http://www.google.com/') 
    puts "Fetched page #1: #{data.response_header.status}" 

    EventMachine.stop 
    }.resume 
end 

這是偉大的,異步GET請求!好極了!!!但是......我如何實際使用它異步?該示例除了創建包含光纖外沒有其他任何內容。

從我的理解(和不理解):

async_fetch阻塞,直到f.resume被調用。

f是當前光纖,它是在EventMachine.run塊中創建的環繞光纖。

async_fetch將控制流轉回給它的調用者?我不確定這是什麼

爲什麼包裝光纖在最後恢復?光纖是否默認暫停?

在這個例子之外,我該如何使用光纖來表達一些由鍵盤命令觸發的請求?

喜歡,例如:每當我鍵入一個字母,我向谷歌或其他什麼的請求? - 通常這需要一個線程,主線程會告訴並行線程爲每個請求啓動一個線程。 : - \

我是新來的併發/纖維。但他們非常耐人尋味!

如果有人可以回答這些問題,那將非常感謝!

回答

2

有一個很多在Ruby中的纖維混淆。纖維不是實現併發的工具;它們只是一種組織代碼的方式,可以更清楚地表示發生了什麼。

在我看來,'纖維'這個名字與'線索'相似,這有助於混淆。

如果你想真正的併發,也就是分佈在整個CPU負載所有可用的CPU的,你有以下幾種選擇:

在MRI紅寶石

運行多個Ruby VM的(即操作系統的進程) ,使用fork等。即使在Ruby中有多個線程,GIL(全局解釋器鎖)也可以防止Ruby運行時使用超過1個CPU。

JRuby中

與MRI紅寶石,JRuby的將分配線程時使用多個CPU,這樣你就可以得到真正的併發處理。

如果你的代碼花費大部分時間等待外部資源,那麼你可能不需要這種真正的併發。 MRI線程或某種事件處理循環可能適合您。

+0

這絕對是有用的信息!我想現在我只需要弄清楚我是否需​​要線程。我在項目中使用EventMachine,並使用用戶鍵盤輸入 - 在輸入時,可能會發生一些請求。由於一切都已經完成,大部分時間應用程序都處於閒置狀態,你是否說使用線程是不值得的?因爲這個平衡會處理所有事情? – NullVoxPopuli

+0

作爲一個側面說明,在圍繞ruby 3x3進行炒作之後(ruby 3.0比ruby 2.0快3倍),我不知道MRI Ruby是否會在未來使用多個CPU。 – NullVoxPopuli

+1

我曾經在RubyConf上向Matz問過這個問題。他說,不,使用多個CPU的MRI方法正在啓動多個Ruby進程。 –

相關問題