1. 程式人生 > >Linux下 C++ 在類中的多線程技

Linux下 C++ 在類中的多線程技

sleep 是我 調用 目標 阻塞 com turn thread log

有很多時候,我們希望可以在C++類裏面對那些比較耗時的函數使用多線程技術,但是,C++類的成員函數的函數指針不能直接做為參數傳到pthread_create,主要因為是C++成員函數指針帶有類命名空間,同時成員函數末尾是會被C++編譯器加上可以接收對象地址的this指針參數。因此需要將成員函數做一定的轉化,將其轉化為不被編譯器加上this指針,而由我們自己來為該函數維護”this”指針即可。

#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <time.h>
using
namespace std; class Test { public: int sum=0; int cnt; public: int insert(); }; int Test::insert() { sleep(2); cnt+=1; }

如上所示,代碼聲明了一個類Test,假設該類有一個十分耗時的成員函數:insert(),這個函數每次執行需要2000ms的時間。對於如此耗時的函數,我們在設計時都會想方法將其設計為線程函數,這樣調用者才不會阻塞。

於是我們為其加上多線程:

#include <stdio.h>
#include 
<stdlib.h> #include <iostream> #include <time.h> #include <unistd.h> #include <pthread.h> using namespace std; class Test { public: int sum=0; int cnt; public: int insert(); void * insert_pth(void*); void lanch(); }; int Test::insert() { sleep(
2); sum+=1; } void * Test::insert_pth(void*) { insert(); } void Test::lanch() { pthread_t pth; pthread_create(&pth,NULL,insert_pth,NULL); } int main() { Test t; t.lanch(); return 0; }

以上代碼通過調用lanch()來創建多線程來執行insert_pth,insert_pth 再調用insert()。但是 這樣的代碼在編譯時即會報錯:

技術分享圖片

只需將insert_pth變化為static函數,同時將insert邏輯代碼轉移到insert_pth即可:

#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <time.h>
#include <unistd.h>
#include <pthread.h>
using namespace std;
class Test
{
    public:
        int sum=0;
        int cnt;
    public:
        int insert();
    static  void * insert_pth(void*);
        void lanch();
};void * Test::insert_pth(void* __this)
{
    Test * _this =(Test *)__this;
    sleep(2);
    _this->sum+=1;
    printf("%d insert.....\n",_this->sum);
}
void Test::lanch()
{
    pthread_t pth;
    pthread_create(&pth,NULL,insert_pth,(void*)this);
}
int main()
{
    Test t;
    t.sum=0;
    t.lanch();
    sleep(5);
    return 0;
}

註意:

使用多線程處理耗時成員函數的步驟:
1. 聲明另外一個靜態函數:static void XXX_pth(void __this);
該函數與目標成員函數在函數名盡量保持一致 。

2. 將原成員函數的代碼拷貝至void * XXX_pth(void * __this);
在 XXX_pth()開始處將void * __this 轉化為 對象的指針 ObjectPoint _this; 將拷貝下來的所有成員變量加上_this->

3. 編寫線程啟動代碼。
pthread_create()最後一個參數傳入this指針

4.編譯時需要加上-lpthread選項。

Linux下 C++ 在類中的多線程技