一、线程的传参
#include<iostream>
#include<thread>
#include<string>
using namespace std;
void threadtest(int a,double b,string str)
{
this_thread::sleep_for(100ms);
cout << a << " " << b << " " << str << endl;
}
int main()
{
thread th;
{
int a = 1;
int b = 2;
string str = "3";
th = thread(threadtest, a, b, str);
}
th.join();
return 0;
}
首先我们知道,{}里面的变量会存在栈中,在大括号结束后,栈中的变量会销毁掉,那么线程传参的变量按理说应该找不到才是,然而答案是依旧能正常输出结果。
原因:
在thread源码中,线程会单独将传入的参数拷贝一份,拷贝到列表中,再将列表中的值传入到线程句柄中。
拷贝构造函数详解
二、参数传递的一些坑
1、传递的空间被销毁掉(其生命周期小于线程的生命周期)
可以看到这里对象t已经被析构函数先析构掉了,导致线程运行的时候已经找不到引用的对象t的空间了。当然我们可以把对象创建到堆上来解决这类情况
2、传递引用
当我们传递引用的时候,代码会报错
原因是它的模板源码当中没法判断你传递的是否是引用参数
我们需要加一个ref()函数来声明一下是引用变量就可以解决
std::ref()函数接受一个对象作为参数,并返回一个引用包装器。
std::ref()函数的作用在于,在函数模板中可以使用引用参数,而不是拷贝参数,这通常可以提高代码的性能。