Linux執行緒池

2021-06-07 10:00:32 字數 1906 閱讀 6335

linux下通用執行緒池的建立與使用

本文給出了乙個通用的執行緒池框架,該框架將與執行緒執行相關的任務進行了高層次的抽象,使之與具體的執行任務無關。另外該執行緒池具有動態伸縮性,它能根據執行任務的輕重自動調整執行緒池中線程的數量。文章的最後,我們給出乙個簡單示例程式,通過該示例程式,我們會發現,通過該執行緒池框架執行多執行緒任務是多麼的簡單。

為什麼需要執行緒池

目前的大多數網路伺服器,包括web伺服器、email伺服器以及資料庫伺服器等都具有乙個共同點,就是單位時間內必須處理數目巨大的連線請求,但處理時間卻相對較短。

傳統多執行緒方案中我們採用的伺服器模型則是一旦接受到請求之後,即建立乙個新的執行緒,由該執行緒執行任務。任務執行完畢後,執行緒退出,這就是是「即時建立,即時銷毀」的策略。儘管與建立程序相比,建立執行緒的時間已經大大的縮短,但是如果提交給執行緒的任務是執行時間較短,而且執行次數極其頻繁,那麼伺服器將處於不停的建立執行緒,銷毀執行緒的狀態。

我們將傳統方案中的執行緒執行過程分為三個過程:t1、t2、t3。

t1:執行緒建立時間

t2:執行緒執行時間,包括執行緒的同步等時間

t3:執行緒銷毀時間

那麼我們可以看出,執行緒本身的開銷所佔的比例為(t1+t3) / (t1+t2+t3)。如果執行緒執行的時間很短的話,這比開銷可能佔到20%-50%左右。如果任務執行時間很頻繁的話,這筆開銷將是不可忽略的。

除此之外,執行緒池能夠減少建立的執行緒個數。通常執行緒池所允許的併發執行緒是有上界的,如果同時需要併發的執行緒數超過上界,那麼一部分執行緒將會等待。而傳統方案中,如果同時請求數目為2000,那麼最壞情況下,系統可能需要產生2000個執行緒。儘管這不是乙個很大的數目,但是也有部分機器可能達不到這種要求。

因此執行緒池的出現正是著眼於減少執行緒池本身帶來的開銷。執行緒池採用預建立的技術,在應用程式啟動之後,將立即建立一定數量的執行緒(n1),放入空閒佇列中。這些執行緒都是處於阻塞(suspended)狀態,不消耗cpu,但占用較小的記憶體空間。當任務到來後,緩衝池選擇乙個空閒執行緒,把任務傳入此執行緒中執行。當n1個執行緒都在處理任務後,緩衝池自動建立一定數量的新執行緒,用於處理更多的任務。在任務執行完畢後執行緒也不退出,而是繼續保持在池中等待下一次的任務。當系統比較空閒時,大部分執行緒都一直處於暫停狀態,執行緒池自動銷毀一部分執行緒,**系統資源。

基於這種預建立技術,執行緒池將執行緒建立和銷毀本身所帶來的開銷分攤到了各個具體的任務上,執行次數越多,每個任務所分擔到的執行緒本身開銷則越小,不過我們另外可能需要考慮進去執行緒之間同步所帶來的開銷。

構建執行緒池框架

一般執行緒池都必須具備下面幾個組成部分:

執行緒池管理器:用於建立並管理執行緒池

工作執行緒: 執行緒池中實際執行的執行緒

任務介面: 儘管執行緒池大多數情況下是用來支援網路伺服器,但是我們將執行緒執行的任務抽象出來,形成任務介面,從而是的執行緒池與具體的任務無關。

任務佇列:執行緒池的概念具體到實現則可能是佇列,鍊錶之類的資料結構,其中儲存執行執行緒。

我們實現的通用執行緒池框架由五個重要部分組成cthreadmanage,cthreadpool,cthread,cjob,cworkerthread,除此之外框架中還包括執行緒同步使用的類cthreadmutex和ccondition。

cjob是所有的任務的基類,其提供乙個介面run,所有的任務類都必須從該類繼承,同時實現run方法。該方法中實現具體的任務邏輯。

cthread是linux中線程的包裝,其封裝了linux執行緒最經常使用的屬性和方法,它也是乙個抽象類,是所有執行緒類的基類,具有乙個介面run。

cworkerthread是實際被排程和執行的執行緒類,其從cthread繼承而來,實現了cthread中的run方法。

cthreadpool是執行緒池類,其負責儲存執行緒,釋放執行緒以及排程執行緒。

cthreadmanage是執行緒池與使用者的直接介面,其遮蔽了內部的具體實現。

cthreadmutex用於執行緒之間的互斥。

ccondition則是條件變數的封裝,用於執行緒之間的同步。

Linux 執行緒池

一.功能 執行緒池中有若干個執行緒,用於執行大量相對短暫的任務 二.功能描述 計算密集型任務 執行緒池中線程個數 cpu個數 i o密集型任務 執行緒池中線程個數 cpu個數 當任務增加時,可以動態增加執行緒池中線程個數,當任務執行完成後,可以動態減少執行緒池中線程個數 運用生產消費者模型,生產者執...

Linux 執行緒池

首先,執行緒池是什麼?顧名思義,就是把一堆開闢好的執行緒放在乙個池子裡統一管理,就是乙個執行緒池。其次,為什麼要用執行緒池,難道來乙個請求給它申請乙個執行緒,請求處理完了釋放執行緒不行麼?也行,但是如果建立執行緒和銷毀執行緒的時間比執行緒處理請求的時間長,而且請求很多的情況下,我們的cpu資源都浪費...

Linux 執行緒池

基礎概念 include include using namespace std include include include class task task void setdata int x,int y int run class threadpool void unlockqueue bo...