天天看點

使用QueueUserWorkerItem實作的線程池封裝

此線程池所依賴的線程類,請參看《一個Windows C++的線程類實作》:

http://blog.csdn.net/huyiyang2010/archive/2010/08/10/5801597.aspx

SystemThreadPool.h

#define __SYSTEM_THREAD_POOL__  

#include "Thread.h"  

#include <list>  

#include <windows.h>  

class CThreadPoolExecutor  

{  

public:  

    CThreadPoolExecutor(void);  

    ~CThreadPoolExecutor(void);  

    /** 

      初始化線程池,建立minThreads個線程 

    **/  

    bool Init(unsigned int maxTaskse);  

      執行任務,若目前任務清單沒有滿,将此任務插入到任務清單,傳回true 

      否則傳回false 

    bool Execute(Runnable * pRunnable);  

      終止線程池,先制止塞入任務, 

      然後等待直到任務清單為空, 

      然後設定最小線程數量為0, 

      等待直到線程數量為空, 

      清空垃圾堆中的任務 

    void Terminate();  

      傳回線程池中目前的線程數量 

    unsigned int GetThreadPoolSize();  

private:  

    static unsigned int WINAPI StaticThreadFunc(void * arg);  

    typedef std::list<Runnable *> Tasks;  

    typedef Tasks::iterator TasksItr;  

    Tasks m_Tasks;  

    CRITICAL_SECTION m_csTasksLock;  

    volatile bool m_bRun;  

    volatile bool m_bEnableInsertTask;  

    volatile unsigned int m_maxTasks;  

};  

#endif  

SytemThreadPool.cpp

#include "SystemThreadPool.h"  

CThreadPoolExecutor::CThreadPoolExecutor(void) :   

m_bRun(false),  

m_bEnableInsertTask(false)  

    InitializeCriticalSection(&m_csTasksLock);  

}  

CThreadPoolExecutor::~CThreadPoolExecutor(void)  

    Terminate();  

    DeleteCriticalSection(&m_csTasksLock);  

bool CThreadPoolExecutor::Init(unsigned int maxTasks)  

    if(maxTasks == 0)  

    {  

        return false;  

    }  

    m_maxTasks = maxTasks;  

    m_bRun = true;  

    m_bEnableInsertTask = true;  

    return true;  

bool CThreadPoolExecutor::Execute(Runnable * pRunnable)  

    if(!m_bEnableInsertTask)  

    if(NULL == pRunnable)  

    EnterCriticalSection(&m_csTasksLock);  

    if(m_Tasks.size() >= m_maxTasks)  

        LeaveCriticalSection(&m_csTasksLock);  

    m_Tasks.push_back(pRunnable);  

    LeaveCriticalSection(&m_csTasksLock);  

    bool ret = QueueUserWorkItem((LPTHREAD_START_ROUTINE)StaticThreadFunc, this, WT_EXECUTEINPERSISTENTIOTHREAD);  

    if(!ret)  

        EnterCriticalSection(&m_csTasksLock);  

        m_Tasks.remove(pRunnable);  

    return ret;  

unsigned int CThreadPoolExecutor::GetThreadPoolSize()  

    return m_Tasks.size();  

void CThreadPoolExecutor::Terminate()  

    m_bEnableInsertTask = false;  

    m_bRun = false;  

    while(m_Tasks.size() != 0)  

        Sleep(1);  

unsigned int WINAPI CThreadPoolExecutor::StaticThreadFunc(void * arg)  

    CThreadPoolExecutor * pThreadPool = (CThreadPoolExecutor *)arg;  

    Runnable * pRunnable = NULL;  

    EnterCriticalSection(&pThreadPool->m_csTasksLock);  

    pRunnable = pThreadPool->m_Tasks.front();  

    if(NULL != pRunnable)  

        pThreadPool->m_Tasks.pop_front();  

    LeaveCriticalSection(&pThreadPool->m_csTasksLock);  

        pRunnable->Run();  

    return 0;  

用法:

#include "Thread.h"

#include "SystemThreadPool.h"

class R : public Runnable

{

public:

    ~R()

    {

    }

    void Run()

        printf("Hello World/n");

};

int _tmain(int argc, _TCHAR* argv[])

    CThreadPoolExecutor * pExecutor = new CThreadPoolExecutor();

    pExecutor->Init(50);

    R r;

    for(int i=0;i<100;i++)

        while(!pExecutor->Execute(&r))

        {

        }

    pExecutor->Terminate();

    delete pExecutor;

    getchar();

    return 0;

}

測試結果:

機器:

Intel(R) Core(TM)2 Duo CPU

E8400 @ 3.00GHz

2G記憶體

對于100個任務并且每個任務包含10000000個循環,任務中無等待:

線程池耗時:2203時間片