1. 程式人生 > >c/c++ 多線程 參數傳遞

c/c++ 多線程 參數傳遞

地址 共享 就會 col int 函數 釋放 font 技術

多線程 參數傳遞

1,值傳遞,拷貝一份新的給新的線程。線程1中有個int變量a,在線程1中啟動線程2,參數是a的值,這時就會拷貝a,線程1和線程2不共享a。

2,引用傳遞,不拷貝一份新的給新的線程。線程1中有個int變量a,在線程1中啟動線程2,參數是a的引用,這時就不會拷貝a,線程1和線程2共享a。※傳遞參數時,必須明確指出使用std::ref函數,不寫std::ref,編譯不過。

3,指針傳遞,淺拷貝原來的指針給新的線程。線程1中有個指向int變量a的指針,在線程1中啟動線程2,參數是a的地址,這時就不會拷貝a,只是淺拷貝指向a的指針,線程1和線程2共享a。

4,unique_ptr作為參數傳遞,必須使用move函數

5,函數的指針作為參數傳遞

引用傳遞,指針傳遞的註意事項:因為線程2裏使用的是線程1的變量a,所以如果線程1比線程2提前結束了,結束的同時就會釋放變量a的內存空間,可是這時線程2還沒結束,再去訪問線程1中的變量a的話,就會發生意想不到的錯誤!!!

2,引用傳遞,例子:

一共3個線程,main函數是一個線程,在main函數裏啟動了線程2(f1函數),在線程2(f1函數)裏啟動了線程3(f2函數)。

#include <iostream>
#include <thread>
#include <string>
#include <unistd.h>

using namespace std;

void f2(int& i){
  cout << "f2:" << i << endl;
}
void f1(int& i){
  cout << "f1:" << i << endl;
  int j = 11;
  thread t(f2, ref(j));//-------------->②
  t.detach();
}
int main(){
  int i = 10;
  thread t(f1, ref(i));
  t.detach();//-------------->①
  pthread_exit(NULL);
}

執行結果:

f1:10
f2:0

執行結果分析:

  • 打印出【f1:10】的原因可能是,①處分離線程後,main函數所在的線程還沒有結束,所以i還沒有被釋放掉,所以能打印出10;還有可能是main函數所在的線程雖然已經結束了,但是巧合的是值還是10。
  • 打印出【f2:0】的原因是,②處分離線程後,線程f1已經結束了,所以函數f1裏的j已經被釋放了,這時線程f2再訪問j的時候就是0了。

3,指針傳遞,例子:

一共3個線程,main函數是一個線程,在main函數裏啟動了線程2(f1函數),在線程2(f1函數)裏啟動了線程3(f2函數)。

#include <iostream>
#include <thread>
#include <string>
#include <unistd.h>

using namespace std;

void f2(int* i){
  cout << "f2:" << *i << endl;
}
void f1(int& i){
  cout << "f1:" << i << endl;
  int j = 11;
  thread t(f2, &j);
  t.detach();//-------------->②
}
int main(){
  int i = 10;
  thread t(f1, ref(i));
  t.detach();//-------------->①
  pthread_exit(NULL);
}

執行結果:

f1:10
f2:0

執行結果分析:

  • 打印出【f1:10】的原因可能是,①處分離線程後,main函數所在的線程還沒有結束,所以i還沒有被釋放掉,所以能打印出10;還有可能是main函數所在的線程雖然已經結束了,但是巧合的是值還是10。
  • 打印出【f2:0】的原因是,②處分離線程後,線程f1已經結束了,所以函數f1裏的j已經被釋放了,這時線程f2再訪問j的時候就是0了。

4,unique_ptr作為參數傳遞,必須使用move函數

#include <iostream>
#include <thread>
#include <string>
#include <unistd.h>

using namespace std;

void f1(unique_ptr<int> upt){
  cout << *upt << endl;
}

int main(){
  unique_ptr<int> upt(new int(10));
  //必須使用move函數,否則編譯不過
  thread t(f1, move(upt));
  t.detach();
  pthread_exit(NULL);
}

5,函數的指針作為參數傳遞

#include <iostream>
#include <thread>
#include <string>
#include <unistd.h>

using namespace std;

class Test{
public:
  void func(int& i){
    cout << i << endl;
  }
};
int main(){
  Test da;
  int i = 10;
  //&Test::func為對象的方法的指針,&da為對象的指針,ref(i)是方法func的參數
  thread t(&Test::func, &da, ref(i));
  t.detach();
  pthread_exit(NULL);
}

c/c++ 學習互助QQ群:877684253

技術分享圖片

本人微信:xiaoshitou5854

c/c++ 多線程 參數傳遞