平时的开发中,我们势必用到线程,不可能所有的逻辑在主线程中解决。
直接上代码,记录我平时的线程应用。
头文件:
#ifndef __XLIB_LIB_COMM_THREAD_H__
#define __XLIB_LIB_COMM_THREAD_H__
#pragma warning( push )
#pragma warning( disable : 4244 )
#include <boost/thread.hpp>
#pragma warning( pop )
namespace CxxAThread
{
const size_t THREAD_INFO_LEN = 128;
class CThread
{
public:
CThread(void);
virtual ~CThread(void);
bool Start(bool bSuspended = false);
void WaitFor();
void Terminate(void);
bool IsStarted() { return m_isstart; }
bool IsTerminate() { return m_bTerminated; }
string GetThreadInfo() { return m_ThreadInfo; }
void SetThreadInfo(string strInfo);
virtual void ReleaseSource() {}
protected:
virtual void ExecuteOne(bool &iswaiting) = 0;
private:
void ImpExecute();
private:
char m_ThreadInfo[128];
bool m_isstart;
boost::thread * m_pthread;
private:
boost::mutex m_mut;
unsigned int m_threadid;
unsigned m_ALiveTm;
protected:
volatile bool m_bTerminated;
};
class CThreadPool
{
public:
CThreadPool(void)
{
m_lastnotice = CSgsPubFun::GetNowTime();
}
virtual ~CThreadPool(void)
{
if (m_vecThreads.size() > 0)
ShutDown();
}
void AddThread(CThread* pThread) { if (pThread) m_vecThreads.push_back(pThread); }
void Start()
{
for (unsigned int i = 0; i < m_vecThreads.size(); i++)
{
CThread* pThread = m_vecThreads[i];
if (!pThread->IsStarted())
pThread->Start();
}
}
void NoticeRun()
{
unsigned iServerTmA = CSgsPubFun::GetNowTime();
if (iServerTmA - m_lastnotice < 0)
return;
m_lastnotice = iServerTmA;
}
void ShutDown()
{
for (unsigned int i = 0; i < m_vecThreads.size(); i++)
m_vecThreads[i]->Terminate();
while (m_vecThreads.size() > 0)
{
CThread* pThread = m_vecThreads[0];
pThread->WaitFor();
delete pThread;
m_vecThreads.erase(m_vecThreads.begin());
}
}
size_t GetThreadCount() { return m_vecThreads.size(); }
CThread* GetThread(unsigned int nIndex)
{
if (nIndex >= m_vecThreads.size())
return NULL;
return m_vecThreads[nIndex];
}
protected:
std::vector<CThread*> m_vecThreads;
unsigned int m_lastnotice;
};
}
#endif
源文件实现:
#include "./CxxThread.h"
CxxAThread::CThread::CThread(void)
{
m_ALiveTm = 0;
m_pthread = 0;
m_isstart = false;
m_bTerminated = false;
memset(m_ThreadInfo, 0, sizeof(m_ThreadInfo));
static unsigned int sc_threadid = 0;
m_threadid = sc_threadid++;
}
CxxAThread::CThread::~CThread(void)
{
}
void CxxAThread::CThread::WaitFor(void)
{
while (m_isstart)
{
boost::this_thread::sleep(boost::posix_time::milliseconds(1));
}
boost::this_thread::sleep(boost::posix_time::milliseconds(1));
}
void CxxAThread::CThread::SetThreadInfo(string strInfo)
{
CSgsPubFun::strcpy(m_ThreadInfo, sizeof(m_ThreadInfo), strInfo.c_str());
}
bool CxxAThread::CThread::Start(bool bSuspended)
{
static int sc_threadindex = 0;
m_bTerminated = false;
m_pthread = new boost::thread(boost::bind(&CThread::ImpExecute, this));
m_isstart = true;
sc_threadindex++;
return true;
}
void CxxAThread::CThread::Terminate(void)
{
m_bTerminated = true;
}
void CxxAThread::CThread::ImpExecute()
{
unsigned iServerTmA = GetNowTime();
bool iswaiting = false;
boost::unique_lock<boost::mutex> lock(m_mut);
while (true)
{
if (m_bTerminated)
break;
try
{
this->ExecuteOne(iswaiting);
}
catch (...)
{
//break;
}
iServerTmA = GetNowTime();
if (iServerTmA - m_ALiveTm > 10)
{
m_ALiveTm = iServerTmA;
}
}
m_isstart = false;
this->ReleaseSource();
}