C++线程池的实现(二)

参考文章:http://blog.csdn.net/huyiyang2010/archive/2010/08/10/5801597.aspx

 1 // CThread.h
 2 
 3 #ifndef __MY_THREAD_H__
 4 #define __MY_THREAD_H__
 5 
 6 #include   <windows.h>
 7 #include   <process.h>
 8 
 9 // 线程执行接口
10 class CRunnable
11 {
12 public:
13     CRunnable(){}
14     virtual ~CRunnable() {}
15     virtual void Run() = 0;
16 };
17 
18 class CThread : public CRunnable
19 {
20     enum
21     {
22         enmMaxThreadNameLen = 64,
23     };
24 private:
25     explicit CThread(const CThread & rhs);
26 public:
27     CThread();
28     CThread(CRunnable * pRunnable);
29 
30     ~CThread(void);
31     bool Start();
32     virtual void Run();
33     void Join(int timeout = -1);
34     void Resume();
35     void Suspend();
36     bool Terminate(unsigned long ExitCode);
37     void dump();
38     unsigned int GetThreadID();
39     friend bool operator==(const CThread& left,const CThread& right);
40 private:
41     static unsigned int WINAPI StaticThreadFunc(void * arg);
42     void init();
43 private:
44     HANDLE m_hHandle;
45     CRunnable * const m_pRunnable;
46     unsigned int m_nThreadID;
47     volatile bool m_bRun;
48 };
49 
50 #endif
View Code
  1 #include "CThread.h"
  2 #include <iostream>
  3 using namespace std;
  4 
  5 CThread::CThread(void):m_pRunnable(NULL)
  6 {
  7     init();
  8 }
  9 
 10 CThread::CThread(CRunnable * pRunnable):m_pRunnable(pRunnable)
 11 {
 12     init();
 13 }
 14 
 15 CThread::~CThread(void)
 16 {
 17     if(m_pRunnable != NULL )
 18     {
 19         delete m_pRunnable;
 20     }
 21 }
 22 
 23 void CThread::init()
 24 {
 25     m_bRun = false;
 26     m_hHandle = (HANDLE)_beginthreadex(NULL, 0, StaticThreadFunc, this, CREATE_SUSPENDED, &m_nThreadID);
 27 }
 28 
 29 
 30 bool CThread::Start()
 31 {
 32     Resume();
 33     return (NULL != m_pRunnable);
 34 }
 35 
 36 void CThread::Run()
 37 {
 38     if(NULL != m_pRunnable)
 39     {
 40         m_pRunnable->Run();
 41         if(m_pRunnable != NULL)
 42         {
 43             delete m_pRunnable;
 44         }
 45     }
 46 }
 47 
 48 void CThread::Join(int timeout)
 49 {
 50     if(NULL == m_hHandle || m_bRun == false )
 51     {
 52         return;
 53     }
 54     if(timeout <= 0)
 55     {
 56         timeout = INFINITE;
 57     }
 58     ::WaitForSingleObject(m_hHandle, timeout);
 59 }
 60 
 61 void CThread::Resume()
 62 {
 63     if( NULL == m_hHandle || m_bRun == true )
 64     {
 65         return;
 66     }
 67     m_bRun = true;
 68     ::ResumeThread(m_hHandle);
 69 }
 70 
 71 void CThread::Suspend()
 72 {
 73     if(NULL == m_hHandle || m_bRun == false )
 74     {
 75         return;
 76     }
 77     ::SuspendThread(m_hHandle);
 78 }
 79 
 80 bool CThread::Terminate(unsigned long ExitCode)
 81 {
 82     if(NULL == m_hHandle || m_bRun == false )
 83     {
 84         return true;
 85     }
 86     if(::TerminateThread(m_hHandle, ExitCode))
 87     {
 88         ::CloseHandle(m_hHandle);
 89         return true;
 90     }
 91     return false;
 92 }
 93 
 94 unsigned int CThread::GetThreadID()
 95 {
 96     return m_nThreadID;
 97 }
 98 
 99 unsigned int CThread::StaticThreadFunc(void * arg)  
100 {  
101     CThread * pThread = (CThread *)arg;  
102     pThread->Run();
103     pThread->m_bRun = false;
104     return 0;  
105 }
106 
107 void CThread::dump()
108 {
109     cout<<"run="<<m_bRun<<",id="<<m_nThreadID<<endl;
110 }
111 bool operator==(const CThread& left,const CThread& right)
112 {
113     return left.m_nThreadID == right.m_nThreadID;
114 }
View Code
  1 #ifndef _STATIC_QUEUE_H_
  2 #define _STATIC_QUEUE_H_
  3 
  4 // 静态queue模板,用数组实现的队列,在初始化的时候需要指定长度
  5 template<class T>
  6 class Static_Queue{
  7 public:
  8     Static_Queue();
  9     virtual ~Static_Queue();
 10     bool init(const unsigned int size);
 11     bool push(T t);
 12     bool pop(T & t);
 13     unsigned int GetElementCnt();
 14     void dump();
 15 private:
 16     volatile unsigned int m_nSize;
 17     T *m_arrT;
 18     volatile unsigned int m_nHead;
 19     volatile unsigned int m_nTail;
 20     volatile unsigned int m_nEmptyCnt;
 21 };
 22 
 23 
 24 template<class T>
 25 Static_Queue<T>::Static_Queue()
 26 {
 27     m_nSize = 0;
 28     m_arrT = NULL;
 29     m_nEmptyCnt = 0;
 30     m_nHead = 0;
 31     m_nTail = 0;
 32 }
 33 
 34 template<class T>
 35 Static_Queue<T>::~Static_Queue()
 36 {
 37     delete[] m_arrT;
 38     m_arrT = NULL;
 39 }
 40 
 41 template<class T>
 42 bool Static_Queue<T>::init(const unsigned int size)
 43 {
 44     m_nSize = size;
 45     m_arrT = new T[m_nSize];
 46     if(m_arrT == NULL)
 47     {
 48         return false;
 49     }
 50     memset(m_arrT,0,sizeof(T)*m_nSize);
 51     m_nEmptyCnt = m_nSize;
 52     return true;
 53 }
 54 
 55 template<class T>
 56 bool Static_Queue<T>::push(T t)
 57 {
 58     if( m_nEmptyCnt <= 0 )
 59     {
 60         return false;
 61     }
 62     m_arrT[m_nTail++] = t;
 63     if(m_nTail >= m_nSize)
 64     {
 65         m_nTail = 0;
 66     }
 67     m_nEmptyCnt--;
 68     return true;
 69 }
 70 
 71 template<class T>
 72 bool Static_Queue<T>::pop(T & t)
 73 {
 74     if( m_nEmptyCnt >= m_nSize )
 75     {
 76         return false;
 77     }
 78     t = m_arrT[m_nHead++];
 79     if( m_nHead >= m_nSize )
 80     {
 81         m_nHead = 0;
 82     }
 83     m_nEmptyCnt++;
 84     return true;
 85 }
 86 
 87 template<class T>
 88 unsigned int Static_Queue<T>::GetElementCnt()
 89 {
 90     return m_nSize - m_nEmptyCnt;
 91 }
 92 
 93 template<class T>
 94 void Static_Queue<T>::dump()
 95 {
 96     cout<<"head= "<<m_nHead<<" "<<"tail= "<<m_nTail<<endl;
 97     cout<<"[";
 98     for(int i = 0;i < m_nSize;i++ )
 99     {
100         cout<<m_arrT[i]<<" ";
101     }
102     cout<<"]"<<endl;
103 }
104 
105 
106 #endif
View Code
  1 #ifndef _MY_HASH_INT_H_
  2 #define _MY_HASH_INT_H_
  3 
  4 template<class T,class K>
  5 class HashInt{
  6 public:
  7     HashInt();
  8     virtual ~HashInt();
  9 private:
 10     typedef struct tagElement 
 11     {
 12         T data;
 13         K key;
 14         bool use;
 15         tagElement(){use = false;}
 16         ~tagElement(){}
 17     }Element;
 18     volatile unsigned int m_nSize;
 19     Element *m_arrT;
 20     volatile unsigned int m_nElementCnt;
 21     // 查找
 22     bool find(K key,unsigned int &index);
 23 public:
 24     // 初始化,分配内存
 25     bool init(const unsigned int size);
 26     // 哈希函数
 27     unsigned int hash(K key);
 28     // ELF哈希函数
 29     unsigned int hash_elf(char *str);
 30     // 插入
 31     bool insert(T data,K key);
 32     // 删除
 33     bool remove(K key);
 34     // 查找
 35     bool find(K key,T &data);
 36     // 修改
 37     bool modify(T data,K key);
 38     // 元素个数
 39     unsigned int get_element_cnt();
 40     // 下标索引
 41     bool get_by_index(unsigned int index,T &data);
 42     void dump();
 43 };
 44 
 45 template<class T,class K>
 46 bool HashInt<T, K>::get_by_index( unsigned int index,T &data )
 47 {
 48     if( m_nElementCnt == 0)
 49     {
 50         return false;
 51     }
 52     if(m_arrT[index].use == false)
 53     {
 54         return false;
 55     }
 56     data = m_arrT[index].data;
 57     return true;
 58 }
 59 
 60 template<class T,class K>
 61 unsigned int HashInt<T, K>::get_element_cnt()
 62 {
 63     return m_nElementCnt;
 64 }
 65 
 66 template<class T,class K>
 67 unsigned int HashInt<T, K>::hash_elf( char *str)
 68 {
 69     unsigned int locate = 0;
 70     unsigned int x = 0;
 71     while (*str)
 72     {
 73         locate = (locate << 4) + (*str++);//hash左移4位,当前字符ASCII存入hash低四位。 
 74         if ((x = locate & 0xF0000000L) != 0)
 75         {//如果最高的四位不为0,则说明字符多余7个,如果不处理,再加第九个字符时,第一个字符会被移出,因此要有如下处理。
 76             locate ^= (x >> 24);
 77             //清空28-31位。
 78             locate &= ~x;
 79         }
 80     }
 81     return locate%m_nSize;
 82 }
 83 
 84 template<class T,class K>
 85 HashInt<T, K>::~HashInt()
 86 {
 87     if(m_arrT != NULL)
 88     {
 89         delete[] m_arrT;
 90     }
 91 }
 92 
 93 template<class T,class K>
 94 HashInt<T, K>::HashInt()
 95 {
 96     m_arrT = NULL;
 97     m_nSize = 0;
 98     m_nElementCnt = 0;
 99 }
100 
101 template<class T,class K>
102 void HashInt<T, K>::dump()
103 {
104     cout<<"m_nElementCnt="<<m_nElementCnt<<",m_nSize="<<m_nSize<<endl;
105     for(unsigned int i = 0;i < m_nSize;i++)
106     {
107         if(m_arrT[i].use == true)
108         {
109             cout<<i<<"-";
110             cout<<"["<<m_arrT[i].key<<"="<<m_arrT[i].data<<"] ";
111         }
112     }
113     cout<<endl;
114 }
115 
116 template<class T,class K>
117 bool HashInt<T, K>::modify( T data,K key )
118 {
119     if( m_nElementCnt == 0)
120     {
121         return false;
122     }
123     bool exist = false;
124     unsigned int index;
125     exist = find(key,index);
126     if( exist == true )
127     {
128         m_arrT[index].data = data;
129     }
130     return false;
131 }
132 
133 template<class T,class K>
134 bool HashInt<T, K>::find( K key,T &data )
135 {
136     if( m_nElementCnt == 0)
137     {
138         return false;
139     }
140     bool exist = false;
141     unsigned int index;
142     exist = find(key,index);
143     if( exist == true )
144     {
145         data = m_arrT[index].data;
146         return true;
147     }
148     return false;
149 }
150 
151 
152 template<class T,class K>
153 bool HashInt<T, K>::find( K key,unsigned int &index )
154 {
155     if( m_nElementCnt == 0)
156     {
157         return false;
158     }
159     unsigned int locate = hash(key),i = 1;
160     while(i < m_nSize)
161     {
162         if( m_arrT[locate].use == true &&  m_arrT[locate].key == key)
163         {
164             index = locate;
165             return true;
166         }
167         locate = (locate + i)%m_nSize;
168         i++;
169     }
170     return false;
171 }
172 
173 
174 template<class T,class K>
175 bool HashInt<T, K>::remove( K key )
176 {
177     // 表为空
178     if( m_nElementCnt == 0 )
179     {
180         return false;
181     }
182     bool exist = false;
183     unsigned int index;
184     exist = find(key,index);
185     if( exist == true )
186     {
187         m_arrT[index].use = false;
188         m_nElementCnt--;
189         return true;
190     }
191     return false;
192 }
193 
194 template<class T,class K>
195 bool HashInt<T, K>::insert( T data,K key)
196 {
197     // 表已满
198     if( m_nElementCnt == m_nSize )
199     {
200         return false;
201     }
202     unsigned int locate = hash(key),i = 1;
203     while(i < m_nSize)
204     {
205         if( m_arrT[locate].use == false)
206         {
207             m_arrT[locate].data = data;
208             m_arrT[locate].key = key;
209             m_arrT[locate].use = true;
210             m_nElementCnt++;
211             return true;
212         }
213         locate = (locate + i)%m_nSize;
214         i++;
215     }
216     return false;
217 }
218 
219 template<class T,class K>
220 unsigned int HashInt<T, K>::hash( K key )
221 {
222     return key%m_nSize;
223 }
224 
225 template<class T,class K>
226 bool HashInt<T, K>::init( const unsigned int size )
227 {
228     m_nSize = size;
229     m_arrT = new Element[m_nSize];
230     m_nElementCnt = 0;
231     //cout<<"size = "<<sizeof(Element)*m_nSize<<endl;
232     return true;
233 }
234 
235 #endif
View Code
 1 #ifndef __MY_MY_THREAD_POOL_H_
 2 #define __MY_MY_THREAD_POOL_H_
 3 
 4 #include "CThread.h"
 5 #include <windows.h>
 6 #include "StaticQueue.h"
 7 #include "HashInt.h"
 8 
 9 using namespace std;
10 
11 class CMyThreadPool
12 {
13 public:
14     CMyThreadPool(void);
15     virtual ~CMyThreadPool(void);
16     // 初始化线程池,创建minThreads个线程 
17     bool Initialize(unsigned int minThreadCnt,unsigned int maxThreadCnt,unsigned int maxTaskQueueLength);
18     bool AddTask( CRunnable *pRunnable, bool bRun = true);
19     void Terminate();
20     // 获取线程数量
21     unsigned int GetThreadCnt();
22 private:
23     // 从任务队列头中取出一个任务
24     CRunnable *GetTask();
25     // 执行任务线程
26     static unsigned int WINAPI StaticThreadFunc(void * arg);
27 private:
28     // 工作者类
29     class CWorker : public CThread
30     {
31     public:  
32         CWorker(CMyThreadPool *pThreadPool,CRunnable *pFirstTask = NULL);
33         ~CWorker();  
34         void Run();  
35     private:
36         CMyThreadPool * const m_pThreadPool;
37         CRunnable * m_pFirstTask;
38         volatile bool m_bRun;  
39     };
40 
41     typedef HashInt<CWorker*,unsigned int> ThreadPool;  
42     typedef Static_Queue<CRunnable *> Tasks;  
43 
44     CRITICAL_SECTION m_csTasksLock;  
45     CRITICAL_SECTION m_csThreadPoolLock;  
46 
47     // 线程池
48     ThreadPool m_ThreadPool;  
49     // 垃圾线程
50     ThreadPool m_TrashThread;  
51     // 任务队列
52     Tasks m_Tasks;
53     // 是否在运行
54     volatile bool m_bRun;  
55     // 能否插入任务
56     volatile bool m_bEnableInsertTask;  
57     // 最小线程数
58     volatile unsigned int m_minThreads;  
59     // 最大线程数
60     volatile unsigned int m_maxThreads;  
61     // 最大挂起任务数量
62     volatile unsigned int m_maxPendingTasks;  
63 };
64 
65 #endif
View Code
  1 #include "CMyThreadPool.h"
  2 #include <iostream>
  3 #include <time.h>
  4 
  5 using namespace std;
  6 
  7 CMyThreadPool::CWorker::CWorker(CMyThreadPool *pThreadPool,CRunnable *pFirstTask)
  8     :m_pThreadPool(pThreadPool),m_pFirstTask(pFirstTask),m_bRun(true)
  9 {
 10 
 11 }
 12 
 13 CMyThreadPool::CWorker::~CWorker()
 14 {
 15 
 16 }
 17 
 18 void CMyThreadPool::CWorker::Run()
 19 {
 20     CRunnable * pTask = NULL;
 21     while(m_bRun)
 22     {
 23         // 取出一个任务
 24         if(NULL == m_pFirstTask)  
 25         {  
 26             pTask = m_pThreadPool->GetTask();  
 27         }  
 28         else  
 29         {  
 30             pTask = m_pFirstTask;  
 31             m_pFirstTask = NULL;  
 32         }  
 33         // 如果没有取到任务
 34         if(NULL == pTask)
 35         {
 36             EnterCriticalSection(&(m_pThreadPool->m_csThreadPoolLock));
 37             // 如果运转的线程数大于最小线程数,需要清除多余的线程
 38             if(m_pThreadPool->GetThreadCnt() > m_pThreadPool->m_minThreads)  
 39             {
 40                 CWorker *p = NULL;
 41                 unsigned int thread_id = this->GetThreadID();
 42                 if(m_pThreadPool->m_ThreadPool.find(thread_id,p) == true)
 43                 {
 44                     if(p == NULL)
 45                     {
 46                         cout<<"find failed,p == NULL,thread_id = "<<thread_id<<endl;
 47                         continue;
 48                     }
 49                     m_pThreadPool->m_ThreadPool.remove(thread_id);
 50                     m_pThreadPool->m_TrashThread.insert(p,thread_id); 
 51                 }
 52                 else
 53                 {
 54                     cout<<"find by thread_id failed,thread_id = "<<thread_id<<endl;
 55                 }
 56                 m_bRun = false;  
 57             }  
 58             else  
 59             {  
 60                 // 等待已经开始运行的线程结束
 61                 for(unsigned int i = 0;i < m_pThreadPool->m_TrashThread.get_element_cnt();i++)
 62                 {
 63                     CWorker *p = NULL;
 64                     if(m_pThreadPool->m_TrashThread.get_by_index(i,p) == true)
 65                     {
 66                         if(p == NULL)
 67                         {
 68                             cout<<"get_by_index failed,p == NULL"<<endl;
 69                             continue;
 70                         }
 71                         p->Join();
 72                         m_pThreadPool->m_TrashThread.remove(p->GetThreadID());
 73                         delete p;
 74                     }
 75                 }
 76             }  
 77             LeaveCriticalSection(&(m_pThreadPool->m_csThreadPoolLock));  
 78             continue;  
 79         }
 80         else  
 81         {  
 82             pTask->Run();
 83             delete pTask;
 84             pTask = NULL;  
 85         }
 86     }
 87 }
 88 
 89 
 90 CMyThreadPool::CMyThreadPool(void):m_bRun(false),m_bEnableInsertTask(false)  
 91 {
 92     InitializeCriticalSection(&m_csTasksLock);  
 93     InitializeCriticalSection(&m_csThreadPoolLock);  
 94 }
 95 
 96 CMyThreadPool::~CMyThreadPool(void)
 97 {
 98     DeleteCriticalSection(&m_csTasksLock);  
 99     DeleteCriticalSection(&m_csThreadPoolLock);  
100 }
101 
102 bool CMyThreadPool::Initialize(unsigned int minThreadCnt,unsigned int maxThreadCnt,unsigned int maxTaskQueueLength)
103 {
104     if(minThreadCnt == 0)  
105     {  
106         return false;  
107     }  
108     if(minThreadCnt > maxThreadCnt)  
109     {  
110         return false;  
111     }
112     if(m_ThreadPool.init(maxThreadCnt) == false 
113         || m_TrashThread.init(maxThreadCnt) == false 
114         || m_Tasks.init(maxTaskQueueLength) == false)
115     {
116         return false;
117     }
118     m_minThreads = minThreadCnt;  
119     m_maxThreads = maxThreadCnt;  
120     m_maxPendingTasks = maxTaskQueueLength;
121     unsigned int i = m_ThreadPool.get_element_cnt();
122     for(; i<minThreadCnt; i++)  
123     {  
124         //创建线程 minThreadCnt 个线程
125         CWorker * pWorker = new CWorker(this);  
126         if(NULL == pWorker)  
127         {  
128             return false;  
129         }  
130         EnterCriticalSection(&m_csThreadPoolLock);
131         if(m_ThreadPool.insert(pWorker,pWorker->GetThreadID()) == false)
132         {
133             return false;
134         }
135         LeaveCriticalSection(&m_csThreadPoolLock);
136         pWorker->Start();
137     }
138     // 可以开始插入任务队列
139     m_bRun = true;
140     m_bEnableInsertTask = true;
141     return true;
142 }
143 
144 unsigned int CMyThreadPool::GetThreadCnt()
145 {
146     return m_ThreadPool.get_element_cnt();
147 }
148 
149 CRunnable * CMyThreadPool::GetTask()
150 {
151     CRunnable *Task = NULL;  
152     EnterCriticalSection(&m_csTasksLock);  
153     if( m_Tasks.GetElementCnt() != 0 )  
154     {  
155         m_Tasks.pop(Task);
156     }  
157     LeaveCriticalSection(&m_csTasksLock);  
158     return Task;  
159 }
160 
161 bool CMyThreadPool::AddTask( CRunnable *pRunnable, bool bRun /*= true*/ )
162 {
163     if(m_bEnableInsertTask == false)
164     {
165         return false;
166     }
167     if(NULL == pRunnable)
168     {
169         return false;
170     }
171     // 如果达到最大挂起任务数量
172     if(m_Tasks.GetElementCnt() >= m_maxPendingTasks)  
173     {  
174         // 如果小于最大线程数
175         if(m_ThreadPool.get_element_cnt() < m_maxThreads)  
176         {  
177             CWorker * pWorker = new CWorker(this, pRunnable);  
178             if(NULL == pWorker)  
179             {  
180                 cout<<"error:CWorker * pWorker = new CWorker(this, pRunnable)"<<endl;
181                 return false;  
182             }  
183             EnterCriticalSection(&m_csThreadPoolLock);  
184             if(m_ThreadPool.insert(pWorker,pWorker->GetThreadID()) == false)
185             {
186                 cout<<"error:m_ThreadPool.insert(pWorker,pWorker->GetThreadID(),id"<<pWorker->GetThreadID()<<endl;
187                 return false;
188             }  
189             LeaveCriticalSection(&m_csThreadPoolLock);  
190             pWorker->Start();  
191         }  
192         else  
193         {  
194             return false;  
195         }  
196     }  
197     else  
198     {  
199         EnterCriticalSection(&m_csTasksLock);  
200         if( m_Tasks.push(pRunnable) == false )
201         {
202             cout<<"error:m_Tasks.push(pRunnable) == false"<<endl;
203             return false;
204         }
205         LeaveCriticalSection(&m_csTasksLock);  
206     }
207     //m_ThreadPool.dump();
208     return true;  
209 }
210 
211 void CMyThreadPool::Terminate()
212 {
213     m_bEnableInsertTask = false;  
214     while(m_Tasks.GetElementCnt() > 0)  
215     {  
216         Sleep(1);  
217     }
218     m_bRun = false;  
219     m_minThreads = 0;  
220     m_maxThreads = 0;  
221     m_maxPendingTasks = 0;  
222     while(m_ThreadPool.get_element_cnt() > 0)  
223     {
224         Sleep(1);  
225     }
226     EnterCriticalSection(&m_csThreadPoolLock);
227     for(unsigned int i = 0;i < m_TrashThread.get_element_cnt();i++)
228     {
229         CWorker *p = NULL;
230         if(m_TrashThread.get_by_index(i,p) == true)
231         {
232             if(p == NULL)
233             {
234                 cout<<"get_by_index failed,p == NULL"<<endl;
235                 return;
236             }
237             p->Join();
238             m_TrashThread.remove(p->GetThreadID());
239         }
240     }
241     LeaveCriticalSection(&m_csThreadPoolLock);
242 }
View Code
 1 #include <iostream>
 2 #include <time.h>
 3 #include <iomanip>
 4 #include "CThread.h"
 5 #include "CThreadPool.h"
 6 #include "CMyThreadPool.h"
 7 
 8 using namespace std;
 9 
10 class R : public CRunnable
11 {
12 public:
13     R(int t):m_nt(t)
14     {
15     }
16     ~R()
17     {
18         cout<<"~R:"<<m_nt<<endl;
19     }
20     void Run()
21     {
22         Sleep(m_nt);
23         cout<<"i am "<<m_nt<<endl;
24     }
25     friend ostream &operator<<(ostream &out,const R &r)
26     {
27         out<<r.m_nt;
28         return out;
29     }
30     friend bool operator < (const R &l,const R &r)
31     {
32         return l < r;
33     }
34     void display()
35     {
36         cout<<m_nt<<" ";
37     }
38     int m_nt;
39 };
40 
41 
42 int main()
43 {
44     R *r1 = new R(200);
45     CMyThreadPool *myThreadPool = new CMyThreadPool();
46     if(myThreadPool->Initialize(1,100,100) == false)
47     {
48         cout<<"inti failed!"<<endl;
49         return 1;
50     }
51     for (int i = 0;i < 20;i++)
52     {
53         R *r = new R(20 -i);
54         if(myThreadPool->AddTask(r) == false)
55         {
56             cout<<"add task failed"<<endl;
57         }
58     }
59     myThreadPool->Terminate();
60     delete myThreadPool;
61     system("pause");
62     return 0;
63 }
View Code
原文地址:https://www.cnblogs.com/tangxin-blog/p/4903745.html