色婷婷AⅤ一区二区三区|亚洲精品第一国产综合亚AV|久久精品官方网视频|日本28视频香蕉

          "); //-->

          博客專欄

          EEPW首頁 > 博客 > C++ 在類里面使用多線程技術(shù)

          C++ 在類里面使用多線程技術(shù)

          發(fā)布人:電子禪石 時間:2022-01-05 來源:工程師 發(fā)布文章

          C++ 在類里面使用多線程技術(shù)

          前言

          有很多時候,我們希望可以在C++類里面對那些比較耗時的函數(shù)使用多線程技術(shù),但是熟悉C++對象語法的人應(yīng)該知道,C++類的成員函數(shù)的函數(shù)指針不能直接做為參數(shù)傳到pthread_create,主要因為是C++成員函數(shù)指針帶有類命名空間,同時成員函數(shù)末尾是會被C++編譯器加上可以接收對象地址的this指針參數(shù)。因此需要將成員函數(shù)做一定的轉(zhuǎn)化,將其轉(zhuǎn)化為不被編譯器加上this指針,而由我們自己來為該函數(shù)維護(hù)”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,假設(shè)該類有一個十分耗時的成員函數(shù):insert(),這個求和函數(shù)每次執(zhí)行需要2000ms的時間。對于如此耗時的函數(shù),我們在設(shè)計時都會想方法將其設(shè)計為線程函數(shù),這樣調(diào)用者才不會阻塞。 
          于是我們?yōu)槠浼由隙嗑€程:

          #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;
          }

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

          pthread.cpp: In member function ‘void Test::lanch()’:
          pthread.cpp:30:42: error: invalid use of non-static member function
            pthread_create(&pth,NULL,insert_pth,NULL);


          只需將insert_pth變化為static函數(shù),同時將insert邏輯代碼轉(zhuǎn)移到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();
          };
          int Test::insert()
          {
              sleep(2);
              sum+=1;
              printf("%d insert.....\n",sum);
          }
          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;
          }

          總結(jié)

          使用多線程處理耗時成員函數(shù)的步驟: 
          1. 聲明另外一個靜態(tài)函數(shù):static void XXX_pth(void __this); 
          該函數(shù)與目標(biāo)成員函數(shù)在函數(shù)名盡量保持一致 
          2. 將原成員函數(shù)的代碼拷貝至void * XXX_pth(void * __this); 
          在 XXX_pth()開始處將void * __this 轉(zhuǎn)化為 對象的指針 ObjectPoint _this; 
          將拷貝下來的所有成員變量加上_this-> 
          3. 編寫線程啟動代碼。 
          注意pthread_create()最后一個參數(shù)傳入this指針

          注意

          在 XXX_pth()函數(shù)內(nèi)容不要調(diào)用類的其它成員函數(shù),否則成員函數(shù)將無法獲取正確的指針而操作錯誤內(nèi)存,從而導(dǎo)致segmantation fault.

          在C++的類中,普通成員函數(shù)不能作為pthread_create的線程函數(shù),如果要作為pthread_create中的線程函數(shù),必須是static !

                  在C語言中,我們使用pthread_create創(chuàng)建線程,線程函數(shù)是一個全局函數(shù),所以在C++中,創(chuàng)建線程時,也應(yīng)該使用一個全局函數(shù)。static定義的類的成員函數(shù)就是一個全局函數(shù)。

           

          更多 參考  http://blog.csdn.net/ksn13/article/details/40538083 


          #include <pthread.h>
          #include <unistd.h>
          #include <stdio.h>
          #include <stdlib.h>
          
          class Thread
          {
              private:
                  pthread_t pid;
              private:
                  static void * start_thread(void *arg);// //靜態(tài)成員函數(shù)
              public: 
                  int start();
                  virtual void run() = 0; //基類中的虛函數(shù)要么實(shí)現(xiàn),要么是純虛函數(shù)(絕對不允許聲明不實(shí)現(xiàn),也不純虛)
          };
          
          int Thread::start()
          {
              if(pthread_create(&pid,NULL,start_thread,(void *)this) != 0) //′創(chuàng)建一個線程(必須是全局函數(shù))
              {    
                  return -1; 
              }    
              return 0;
          }
          
          void* Thread::start_thread(void *arg) //靜態(tài)成員函數(shù)只能訪問靜態(tài)變量或靜態(tài)函數(shù),通過傳遞this指針進(jìn)行調(diào)用
          {
              Thread *ptr = (Thread *)arg;
              ptr->run();  //線程的實(shí)體是run
          }
          
          
          
          class MyThread:public Thread
          {
              public: 
                  void run();
          };
          void MyThread::run()
          {
              printf("hello world\n");
          }
          
          int main(int argc,char *argv[])
          {
              MyThread myThread;
              myThread.start();
              //test.run();
              sleep(1);
              return 0;
          }

          編譯運(yùn)行:

          diego@ubuntu:~/myProg/pthreadCpp$ g++ main.cpp -lpthread
          diego@ubuntu:~/myProg/pthreadCpp$ ./a.out 
          hello world
          diego@ubuntu:~/myProg/pthreadCpp$


          *博客內(nèi)容為網(wǎng)友個人發(fā)布,僅代表博主個人觀點(diǎn),如有侵權(quán)請聯(lián)系工作人員刪除。



          關(guān)鍵詞: C++

          相關(guān)推薦

          技術(shù)專區(qū)

          關(guān)閉