Linux下C++类的线程函数

来源:互联网 发布:赌钱麻将软件 编辑:程序博客网 时间:2024/06/03 14:37

最近在用C++编写一个RTSP的客户端,由于要用到线程,根据C编程的经验,写了如下代码:

class LiRtspSession
{
    public:

       void* MainThreadFunc(void* pvData);

       void* AudioProcThreadFunc(void* pvData);
       void Connect();

       //省略的代码

    private:

        pthread_t     m_hProcHandle, m_hAudioProcHandle;

        //省略的代码

};

 

void LiRtspSession::Connect()
{
    //create main thread creating rtsp session and receiving rtp/rtcp packet
    int ret = pthread_create(&m_hProcHandle, NULL, MainThreadFunc, this);
    if(ret != 0)
    {
         return;
    }

 

    //create a thread receiving audio data
    if(m_bAudioEnabled && m_eProtoType == ptUDP);
    {
         ret = pthread_create(&m_hAudioProcHandle, NULL, AudioProcThreadFunc, this);
         if(ret != 0)
         {
             return;
         }
    }

    pthread_join(m_hProcHandle, NULL);
 
    if(m_bAudioEnabled && m_eProtoType == ptUDP);
    {
          pthread_join(m_hAudioProcHandle, NULL);
    }
}

 

但是在编译时却出现如下错误:

    LiRtspSession.cpp: In member function ‘void LiRtspSession::Connect()’:
    LiRtspSession.cpp:176: error: argument of type ‘void* (LiRtspSession::)(void*)’ does not match ‘void*(*) (void*)’

 

该错误表示:线程创建函数

     pthread_create(pthread_t *restrict tidp,const pthread_attr_t *restrict attr,void*(*start_rtn) (void*),void *restrict arg) 

     的第三个参数类型为:void* (*)(void*),但我们在函数connect函数中给其传入的参数类型却是:

     void* (LiRtspSession::)(void*);于是就出现了类型不匹配的编译错误。

 

经过查看网上的相关讨论以及分析可知,要解决上述类型不匹配的问题有两个方法:

 

一、将线程函数定义为全局函数。

      这样线程函数的类型就为void* (*)(void*),于是传入的实参和函数形参就类型匹配了。而且为了使其能够访问类的成员,可以进一步

      将其定义为类的友元函数。

 

二、将线程函数定义为类的静态成员函数。

      由于c++程序在编译时,编译器会给类的成员函数强加一个this指针,所以成员函数的类型实际上为:

      void* (LiRtspSession::) (void*);

      我们可以通过将线程函数定义为静态函数来消除该this指针,这样线程函数的类型就变为void* (*)(void*)了。而且可以向线程函数

      传入一个this指针,这样线程函数就可以通过this指针来访问类的成员了。

 

考虑到C++编程的风格,我们在这里将线程函数定义为类的静态成员函数;于是,修改后的代码如下:

 

class LiRtspSession
{
    public:

       static void* MainThreadFunc(void* pvData);

       static void* AudioProcThreadFunc(void* pvData);
       void Connect();

       //省略的代码

    private:

        pthread_t     m_hProcHandle, m_hAudioProcHandle;

        //省略的代码

};

 

void* LiRtspSession::MainThreadFunc(void* pvData)

{

     LiRtspSession *pThiz = (LiRtspSession*)pvData;

     //省略的代码

     return NULL;

}

 

void LiRtspSession::Connect()
{
    //create main thread creating rtsp session and receiving rtp/rtcp packet
    int ret = pthread_create(&m_hProcHandle, NULL, MainThreadFunc, this);
    if(ret != 0)
    {
         return;
    }

 

    //create a thread receiving audio data
    if(m_bAudioEnabled && m_eProtoType == ptUDP);
    {
         ret = pthread_create(&m_hAudioProcHandle, NULL, AudioProcThreadFunc, this);
         if(ret != 0)
         {
             return;
         }
    }

    pthread_join(m_hProcHandle, NULL);
 
    if(m_bAudioEnabled && m_eProtoType == ptUDP);
    {
          pthread_join(m_hAudioProcHandle, NULL);
    }
}



 



 

原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 孩子剧烈运动后咳嗽到吐怎么办 前列腺穿刺后血尿一个月了怎么办 两年体检尿潜血2+怎么办严重吗? 尿结石尿不出来堵住了怎么办 四岁宝宝一直咳嗽很厉害怎么办 老公家的事业不想做了怎么办 苹果6sp手机卡顿反应慢怎么办 工程之星x3手薄密码忘了怎么办 煮绿豆汤把绿豆炒焦了怎么办 想问别人问题又不好开口怎么办 宝宝认人晚上哭着找阿姨怎么办呀 在拼多多被商家威胁了怎么办 格来云游戏禁止改画质怎么办 京东换了手机登陆要安全验证怎么办 百度网盘登录总是需要验证码怎么办 在微信群发出视频无法撤回怎么办 百度网盘客户端说网络有风险怎么办 百度网盘绑定的手机号注销了怎么办 百度网盘绑定的手机号不用了怎么办 百度网盘内存怎么清空不了怎么办 百度网盘下载时本地空间不足怎么办 百度网盘文件放到桌面太大怎么办 百度有钱花借款没有钱还怎么办 安心流量包扣了两百多钱怎么办 邮箱里超大附件的文件过期了怎么办 ps时间轴储存出现参数错误怎么办 苹果手机网易云会员支付失败怎么办 鲸钱包网络异常需重新加载怎么办 微信加载联系人失败点击重试怎么办 网易将军令没有帐号怎么绑定怎么办 网易将军令绑定银行卡锁定了怎么办 网易新闻上的视频没有声音怎么办 把登录窗体的宏删掉了怎么办 电脑死机了怎么办也不能关机了 虎牙直播手游无法和队友开麦怎么办 为成年开无手续麽托出车祸怎么办 支付宝商户未签约或合约过期怎么办 我的手机帐号被锁定了怎么办 点错网页下载收发收费信息怎么办 用邮箱注册的微信忘记密码了怎么办 很久不用的邮箱号忘记密码怎么办