在MFC下实现的简单线程池。主要用来处理比较频繁的但又耗时比较短的任务。通过预先创建好的线程能够最快的处理任务,而不会将大量的时间用在创建线程和销毁线程。
具体使用方法为创建线程池对象,派生一个任务子类,具体只需要关心任务类的run函数和任务数据
下载MFC线程池源码:ThreadPoolTest.rar
具体实现代码如下:
//-------------header file----------------
#include <list>
using namespace std;
#include "Task.h"
class CThreadPool;
typedef struct ThreadItem
{
HANDLE hThreadHandle; //线程句柄
DWORD dwThreadID; //线程ID
BOOL bThreadFlag; //线程运行标识
CThreadPool* pThreadPool; //属于哪个线程池
ThreadItem()
{
hThreadHandle=NULL;
dwThreadID=0;
bThreadFlag=FALSE;
pThreadPool=NULL;
}
}ThreadItem;
class CThreadPool
{
public:
CThreadPool();
CThreadPool(int nThreadCount);
virtual ~CThreadPool();
static DWORD WINAPI ThreadFunc(LPVOID lpParameter = NULL);
public:
void AddTask(CTask* pTask);
list<ThreadItem*>* GetThreadItemList(){return m_pThreadItemList;};
list<CTask*>* GetTaskList(){return m_pTaskList;};
void StopAllThread();
void AdjustSize(int nThreadCount); //动态调整线程池规模
protected:
//static
private:
int m_nThreadCount; //线程池中线程的个数
list<ThreadItem*>* m_pThreadItemList;
list<CTask*>* m_pTaskList;
CRITICAL_SECTION m_csThreadQueue;
CRITICAL_SECTION m_csTaskQueue;
};
//--------------cpp file-----------------------------
CThreadPool::CThreadPool()
{
m_nThreadCount=5; //默认创建5个线程
InitializeCriticalSection(&m_csThreadQueue);
InitializeCriticalSection(&m_csTaskQueue);
m_pThreadItemList=new list<ThreadItem*>;
m_pTaskList=new list<CTask*>;
EnterCriticalSection(&m_csThreadQueue);
for (int i=0;i<m_nThreadCount;i++)
{
ThreadItem* pItem=new ThreadItem();
if (pItem)
{
pItem->pThreadPool=this;
pItem->bThreadFlag=TRUE;
pItem->hThreadHandle=CreateThread(NULL, 0, ThreadFunc, (LPVOID)pItem, 0, &pItem->dwThreadID);
TRACE("创建线程 threadid:%d\n",pItem->dwThreadID);
m_pThreadItemList->push_back(pItem);
}
}
LeaveCriticalSection(&m_csThreadQueue);
}
CThreadPool::CThreadPool(int nThreadCount )
{
m_nThreadCount=nThreadCount;
InitializeCriticalSection(&m_csThreadQueue);
InitializeCriticalSection(&m_csTaskQueue);
m_pThreadItemList=new list<ThreadItem*>;
m_pTaskList=new list<CTask*>;
EnterCriticalSection(&m_csThreadQueue);
for (int i=0;i<m_nThreadCount;i++)
{
ThreadItem* pItem=new ThreadItem();
if (pItem)
{
pItem->pThreadPool=this;
pItem->bThreadFlag=TRUE;
pItem->hThreadHandle=CreateThread(NULL, 0, ThreadFunc, (LPVOID)pItem, 0, &pItem->dwThreadID);
TRACE("创建线程 threadid:%d\n",pItem->dwThreadID);
m_pThreadItemList->push_back(pItem);
}
}
LeaveCriticalSection(&m_csThreadQueue);
}
CThreadPool::~CThreadPool()
{
StopAllThread();
DeleteCriticalSection(&m_csThreadQueue);
DeleteCriticalSection(&m_csTaskQueue);
delete m_pTaskList;
delete m_pThreadItemList;
}
void CThreadPool::AddTask( CTask* pTask )
{
EnterCriticalSection(&m_csTaskQueue);
if (m_pTaskList)
{
m_pTaskList->push_back(pTask);
}
LeaveCriticalSection(&m_csTaskQueue);
}
DWORD WINAPI CThreadPool::ThreadFunc( LPVOID lpParameter /*= NULL*/ )
{
ThreadItem* pItem=(ThreadItem*)lpParameter;
if (pItem)
{
while (pItem->bThreadFlag)
{
EnterCriticalSection(&pItem->pThreadPool->m_csTaskQueue);
CTask* pTask=NULL;
if (!pItem->pThreadPool->GetTaskList()->empty())
{
pTask=pItem->pThreadPool->GetTaskList()->front();
}
else
{//任务队列为空
LeaveCriticalSection(&pItem->pThreadPool->m_csTaskQueue);
Sleep(1);
continue;
}
if (pTask)
{
pItem->pThreadPool->GetTaskList()->pop_front();
LeaveCriticalSection(&pItem->pThreadPool->m_csTaskQueue);
TRACE("线程id %d 处理 %s \n",pItem->dwThreadID,pTask->GetData());
pTask->Run();
delete pTask;
continue;
}
LeaveCriticalSection(&pItem->pThreadPool->m_csTaskQueue);
Sleep(5);
}
}
return 0;
}
void CThreadPool::StopAllThread()
{
EnterCriticalSection(&m_csThreadQueue);
while (!m_pThreadItemList->empty())
{
ThreadItem* pThreadItem=m_pThreadItemList->front();
if (pThreadItem)
{
TRACE("结束线程 %d\n",pThreadItem->dwThreadID);
pThreadItem->bThreadFlag=FALSE;
WaitForSingleObject(pThreadItem->hThreadHandle,INFINITE);
m_pThreadItemList->pop_front();
delete(pThreadItem);
}
}
LeaveCriticalSection(&m_csThreadQueue);
}
void CThreadPool::AdjustSize( int nThreadCount )
{
if (nThreadCount==m_nThreadCount && nThreadCount<0)
{
return;
}
if (nThreadCount>m_nThreadCount)
{//需要增加 nThreadCount-m_nThreadCount 个线程
EnterCriticalSection(&m_csThreadQueue);
for (int i=0;i<(nThreadCount-m_nThreadCount);i++)
{
ThreadItem* pItem=new ThreadItem();
if (pItem)
{
pItem->pThreadPool=this;
pItem->bThreadFlag=TRUE;
pItem->hThreadHandle=CreateThread(NULL, 0, ThreadFunc, (LPVOID)pItem, 0, &pItem->dwThreadID);
TRACE("创建线程 threadid:%d\n",pItem->dwThreadID);
m_pThreadItemList->push_back(pItem);
}
}
TRACE("增加 %d 个线程\n",nThreadCount-m_nThreadCount);
m_nThreadCount=nThreadCount;
LeaveCriticalSection(&m_csThreadQueue);
}
if (nThreadCount<m_nThreadCount)
{
EnterCriticalSection(&m_csThreadQueue);
for (int i=0;i<m_nThreadCount-nThreadCount;i++)
{
if (!m_pThreadItemList->empty())
{
ThreadItem* pItem=m_pThreadItemList->back();
m_pThreadItemList->pop_back();
pItem->bThreadFlag=FALSE;
WaitForSingleObject(pItem->hThreadHandle,INFINITE);
delete(pItem);
}
}
TRACE("删除 %d 个线程",m_nThreadCount-nThreadCount);
LeaveCriticalSection(&m_csThreadQueue);
}
}
//------------任务基类------------
class CTask //任务基类
{
public:
CTask();
virtual ~CTask();
void SetData(void* pData){m_pData=pData;};
void* GetData(){return m_pData;};
virtual void Run()=0;
protected:
void* m_pData;
};
独立博客地址: http://www.gddhx.com/post/15.html
461

被折叠的 条评论
为什么被折叠?



