linux下C++对线程的封装

之前一直是使用C语言,前段时间转做C++。无论使用什么语言,多线程编程都是不可或缺的。最近项目中又用到了线程,现在将线程的封装做出总结:

1、线程类中应该包含线程ID、线程的状态以及线程基本操作等。

2、线程需要的基本操作都差不多,唯一不同的是线程执行的函数体。因此大多数操作都可以写在基类中,当需要使用线程时,只需要继承该基类并且实现run函数即可。

基类的定义如下:

 

 1 /*线程基类,封装了线程常用的操作,以后需要使用线程时,只需要继承该类并实现Run函数既可*/
 2 class CThread {
 3 public:
 4 
 5     /*如果不需要为线程传参数,则可以使用这个构造函数*/
 6     CThread()
 7     {
 8         m_ThreadId = 0;
 9     
10         m_iThreadStatus = 0;
11     
12         m_vpParameter = NULL;
13     }
14     
15     /*重载构造函数,该构造函数可以为线程传参数*/
16     CThread(void *vpParameter)
17     {
18         m_ThreadId = 0;
19     
20         m_iThreadStatus = 0;
21         
22         m_vpParameter = cpParameter;
23     }
24     
25     virtual ~CThread();
26 
27     /*线程的启动函数,在该函数中将会创建线程*/
28     int Start(void *Parameter);
29 
30     /*线程的回调函数,在该函数中只是转调run函数*/
31     static void *ThreadCall(void *vpParameter);
32 
33     /*获取线程ID*/
34     pthread_t GetThreadId()
35     {
36         return this->m_ThreadId;
37     }
38     
39     /*获取线程状态*/
40     int GetThreadStatus()
41     {
42         return m_iThreadStatus;
43     }
44     
45     /*获取线程状态*/
46     int GetThreadStatus();
47 
48     /*线程真正工作的函数,这个函数需要在派生类中实现*/
49     virtual void *Run(void *Parameter) = 0;
50 protected:
51 
52     //线程的Id号
53     pthread_t m_ThreadId;
54     
55     //线程状态
56     int       m_iThreadStatus;
57     
58     //线程参数
59     void* m_vpParameter;
60 };
61 
62 inline pthread_t CThread::GetThreadId()
63 {
64     return this->m_ThreadId;
65 }

 

  在线程的回调函数中,只是转掉函数Run。这样设计的原因是因为在C++的回调函数必须是全局函数或者是静态成员函数,否则编译不会通过。而全局函数没有虚函数一说,也没有继承一说(静态函数也没有,静态函数只是限制了作用域的全局函数)。Start函数与线程的回调函数实现如下:

 1 int CThread::Start(void *vpParameter)
 2 {
 3     int ret = pthread_create(&(this->m_ThreadId), NULL, CThread::ThreadCall, vpParameter);//该函数中创建线程
 4     if(0 == ret)
 5     {
 6         return TRUE;
 7     }
 8 
 9     return FAULT;
10 }
11 
12 void *CThread::ThreadCall(void *vpParameter)//线程回调函数
13 {
14     void *vpRet;
15     CThread *pObj = static_cast<CThread *>(vpParameter);//将指针强制性转化成对象
16 
17 
18     vpRet = pObj->Run(m_vpParameter);//调用线程正在执行的函数
19 
20     return vpRet;
21 };

总结:这样设计以后,程序中如果需要其它使用其它线程,可以继承该基类,然后实现Run函数即可。如果需要线程等待等操作则需要在里面添加内容。

 

posted @ 2015-11-23 20:36  zxtp  阅读(1144)  评论(0编辑  收藏  举报