目录
简单流程
第一种:
1.采用async:启动一个异步的任务,创建线程并执行线程处理函数,返回值是future对象。
2.通过future对象中的get()方法获取线程函数的返回值
1.带返回值的普通函数充当线程处理函数
#include <thread>
#include <iostream>
#include <future>
using namespace std;
int ReturnValue()
{
return 100;
}
int main()
{
future<int> t = async(ReturnValue);
cout << t.get() << endl;
return 0;
}
2.以类中的成员函数作为线程处理函数【有输入值和返回值】
#include <thread>
#include <iostream>
#include <future>
#include <chrono>
using namespace std;
class DFTX
{
public:
int ReturnClassOne(int num)
{
cout << "当前线程id:" << this_thread::get_id()<<endl;
num *= 2;
this_thread::sleep_for(chrono::milliseconds(5000));//延迟一下5000毫秒
return num;
}
};
int main()
{
DFTX t1;
auto temp = async(&DFTX::ReturnClassOne, &t1, 10);//DFTX类的成员函数ReturnClassOne,对象是t1,输入10,返回temp;
cout << temp.get() << endl;
return 0;
}
3.async和deferred的使用
async:创建线程,执行线程处理函数
deferred:线程处理函数延迟到我们调用wait和get方法时候才会执行,本质是没有创建子线程
#include <thread>
#include <iostream>
#include <future>
#include <chrono>
using namespace std;
class DFTX
{
public:
int ReturnClassOne(int num)
{
cout << "当前线程id:" << this_thread::get_id()<<endl;
num *= 2;
this_thread::sleep_for(chrono::milliseconds(5000));//延迟一下5000毫秒
return num;
}
};
int main()
{
DFTX t1;
auto temp = async(launch::async,&DFTX::ReturnClassOne, &t1, 10);//launch::async 创建并调用
cout << temp.get() << endl;
auto temp2 = async(launch::deferred, &DFTX::ReturnClassOne, &t1, 50);//在这里并没有发生调用
cout << temp2.get() << endl;//这里才开始调用线程
return 0;
}
第二种:
用thread处理带返回值的线程处理函数
1.通过类模板packaged_task包装线程处理函数
2.通过packaged_task的对象调用get_future获取future对象,再通过get()方法得到子线程处理函数的返回值
1.打包普通函数
#include <thread>
#include <iostream>
#include <future>
#include <chrono>
using namespace std;
int PPAP()
{
return 100;
}
void packThread()
{
packaged_task<int(void)> PackOne(PPAP);//<int(void)>是指返回值为int的函数
thread t1(ref(PackOne));//用ref做一个转换
t1.join();
cout << PackOne.get_future().get() << endl;//获取值
}
int main()
{
packThread();
return 0;
}
2.打包类中的成员函数
#include <thread>
#include <iostream>
#include <future>
#include <chrono>
using namespace std;
class DFTX
{
public:
int papap(int num)
{
num *= 2;
return num;
}
};
void packThread()
{
DFTX p1;
packaged_task<int(int)> pack1(bind(&DFTX::papap,&p1,placeholders::_1));
thread t1(ref(pack1),20);
t1.join();
cout << pack1.get_future().get() << endl;
}
int main()
{
packThread();
return 0;
}
3.打包lambda表达式
#include <thread>
#include <iostream>
#include <future>
#include <chrono>
using namespace std;
class DFTX
{
public:
int papap(int num)
{
num *= 2;
return num;
}
};
void packThread()
{
packaged_task<int(int)> t1([](int num)
{
num *= 10;
return num;
});
thread p1(ref(t1),10);
p1.join();
cout << t1.get_future().get() << endl;
}
int main()
{
packThread();
return 0;
}
第三种:
通过promise获取线程函数“返回值”。
1:通过promise类模板构建对象,通过调用set_value是存储函数需要返回的值
2:通过get_future获取future对象,再通过get()方法获取线程处理函数中值【一旦通过get_future获取到future对象后,就不能再次调用get_future函数来获取新的future对象(除非你创建一个新的)】
一:正常函数
#include <thread>
#include <iostream>
#include <future>
#include <chrono>
using namespace std;
void PromiseTest(promise<int>& SaveData, int data)
{
data *= 3;//计算出值
SaveData.set_value(data);//存储到SaveData里面
}
int main()
{
promise<int> p1;
thread t1(PromiseTest, ref(p1),15);
t1.join();
cout << p1.get_future().get() << endl;
return 0;
}
二:别的子线程获取这个子线程的promise内的数据
#include <thread>
#include <iostream>
#include <future>
#include <chrono>
using namespace std;
void PromiseTest(promise<int>& SaveData, int data)
{
data *= 3;//计算出值
SaveData.set_value(data);//存储到SaveData里面
}
void otherGet(future<int>& SaveData)
{
auto result = SaveData.get();
cout << result<<endl;
}
int main()
{
promise<int> p1;
thread t1(PromiseTest, ref(p1),15);
t1.join();
int nnn = p1.get_future().get();
cout << nnn << endl;//get只能使用一次,否则出错
promise<int> temp;
temp.set_value(nnn);
auto num = temp.get_future();
thread t2(otherGet, ref(num));
t2.join();
return 0;
}