從執行緒的角度,可以將伺服器程式設計分為兩類:單執行緒和多執行緒。
【單執行緒模型】
乙個程序中只有乙個執行緒,由於只有乙個執行緒,所以要實現高效能,必須與 「non-blocking i/o + i/o multiplexing」 相結合,另外 libevent 本身也是單執行緒的。相對於多執行緒,單執行緒 server 沒有執行緒切換以及加鎖的開銷,劣勢是不能充分利用 cpu 的多核優勢,不過,這可以通過多個程序來解決。
另外,這種模型程式設計也很簡單,因為簡單,所以是編寫高效能 server 的首選。
【多執行緒模型】
乙個程序中有多個執行緒,一般來說,可以將這些執行緒分成兩類:i/o執行緒和工作執行緒。由此又可以將多執行緒模型大體分成兩類:單一 i/o 執行緒 + 多個工作執行緒、多個 i/o 執行緒(工作執行緒)。另外,不論是單執行緒,還是多執行緒,non-blocking i/o + i/o multiplexing 都是必選的。
(1) 單一 i/o 執行緒 + 多個工作執行緒
這種模型下,i/o 執行緒負責 event loop 和 i/o 兩部分,工作執行緒負責實際的業務邏輯處理,i/o 執行緒與工作執行緒可以通過佇列/共享記憶體等方式進行資料交換,佇列/共享記憶體的訪問需要加鎖。
實際上,這種模型本質上與上述單執行緒模型是類似的,只不過這裡的業務邏輯交由單獨的工作執行緒進行處理。該模型的另外乙個名字是:半同步/半非同步模型(hs/ha)。
半同步-半非同步(half sync-half async)
乙個偵聽執行緒負責接收請求,並在某個佇列中快取他們。另外一組工作者執行緒負責處理請求。因此接收請求的執行緒並不是處理請求的執行緒。
(2) 多個 i/o 執行緒(工作執行緒)
這種模型下,每個 i/o 執行緒都有乙個 event loop ,此時工作執行緒可有可無,而且通常是沒有,即 i/o 執行緒既處理 i/o ,又進行業務邏輯處理。大家熟悉的 leader/follower(l/f) 以及 muti-reactor(m-r) 模型都屬於這類。其中,memcached 使用的 m-r ,ice 使用的 l/f 。
領導者-跟隨者(leader-follower)
有乙個執行緒是領導者,其餘執行緒是這個執行緒的跟隨者。當請求到達時,領導者首先獲取請求,並在跟隨者中選取乙個作為新的領導者,然後繼續處理請求。因此接受請求的執行緒就是處理請求的執行緒。
【小結】
個人認為:
單執行緒模型實現簡單,如果業務邏輯不複雜,是實現高效能 server 的首選,比如 proxy 之類的 server 。
hs/ha 很清晰,如果業務邏輯很複雜,比如 database ,可以考慮這種模型。
如果你想充分利用多 cpu ,當然可以考慮 l/f 或者 m-r 。但是值得一提的是,l/f 中會有鎖的開銷,而 m-r 中沒有鎖的開銷,但 m-r 的執行緒切換的開銷要高於 l/f 。根據同事的一些測試,對於短連線 l/f 的結果好於 m-r ,而對於長連線,m-r 要好於 l/f 。
Linux網路程式設計 伺服器模型
學習過 軟體工程 吧.軟體工程可是每乙個程式 員 必修 的課程啊.如果你沒有學習過,建議你去看一看.在這一章裡面,我們一起來從軟體工程的角度學習網路程式設計的思想.在我們寫程式之前,我們都 應該從軟體工程的角度規劃好我們的軟體,這樣我們開發軟體的效率才會高.在網路程式裡面,一般的來說都是許多客戶機對...
Linux網路程式設計 伺服器模型
在網路程式裡面,一般的來說都是許多客戶機對應乙個伺服器.為了處理客戶機的請求,對服務端的程式就提出了特殊的要求.我們學習一下目前最常用的伺服器模型.迴圈伺服器 迴圈伺服器在同乙個時刻只可以響應乙個客戶端的請求 併發伺服器 併發伺服器在同乙個時刻可以響應多個客戶端的請求 9.1 迴圈伺服器 udp伺服...
Linux網路程式設計 伺服器模型
併發伺服器模型 在伺服器端採用多工機制 多程序或多執行緒 分別為每個客戶端建立乙個任務來處理,極大地提高了伺服器的併發處理能力 1.tcp迴圈伺服器模型 tcp迴圈伺服器模型工作流程如下 socket bind listen while 1 伺服器端採用迴圈巢狀來實現。外層迴圈依次提取每個客戶端的連...