C++98 标准中并没有线程库的存在,直到 C++11 中才终于提供了多线程的标准库,提供了管理线程、保护共享数据、线程间同步操作、原子操作等类。多线程库对应的头文件是 #include <thread> ,类名为 std::thread 。
int testFun(int numb)
{
cout << "function is runing" << endl;
cout << "this thread ID:"<<std::this_thread::get_id() << endl;
std::chrono::seconds dura(5);
std::this_thread::sleep_for(dura);
return ++numb;
}
调用方式:
//* std::sthread
std::thread func1(&testFun,5);
m_obj.join();
而线程毕竟是比较贴近系统的东西,使用起来仍然不是很方便,特别是线程同步及获取线程运行结果上就更加麻烦。我们不能简单的通过 thread.join() 得到结果,必须定义一个线程共享的变量来传递结果,同时还要考虑线程间的互斥问题。好在 C++11 中提供了一个相对简单的异步接口 std::async ,通过这个接口可以简单的创建线程并通过 std::future 中获取结果。
函数原型:
//(C++11 起) (C++17 前)
template< class Function, class... Args>
std::future<std::result_of_t<std::decay_t<Function>(std::decay_t<Args>...)>>
async( Function&& f, Args&&... args );
//(C++11 起) (C++17 前)
template< class Function, class... Args >
std::future<std::result_of_t<std::decay_t<Function>(std::decay_t<Args>...)>>
async( std::launch policy, Function&& f, Args&&... args );
第一个参数是线程的创建策略
-
std::launch::async
:在调用async就开始创建线程。 -
std::launch::deferred
:延迟加载方式创建线程。调用async时不创建线程,直到调用了future的get或者wait时才创建线程。 - 默认策略是:
std::launch::async | std::launch::deferred
int testFun(int numb)
{
cout << "function is runing" << endl;
cout << "this thread ID:"<<std::this_thread::get_id() << endl;
std::chrono::seconds dura(5);
std::this_thread::sleep_for(dura);
return ++numb;
}
调用:
std::async(std::launch::async,&testFun, 5);
返回值:std::future
std::future
是一个模板类,它提供了一种访问异步操作结果的机制。future_status有三种状态:
- deferred:异步操作还未开始
- ready:异步操作已经完成
- timeout:异步操作超时,主要用于std::future<T>.wait_for()
int testFun(int numb){
cout << "function is runing" << endl;
cout << "this thread ID:"<<std::this_thread::get_id() << endl;
std::chrono::seconds dura(5);
std::this_thread::sleep_for(dura);
return ++numb;
}
调用:
std::future<int> result(std::async(&testFun,5));
result.get();
std::promise
std::promise 是C++11并发编程中常用的一个类,常配合std::future使用。其作用是在一个线程t1中保存一个类型typename T的值,可供相绑定的std::future对象在另一线程t2中获取。
int testPromiss ( std::promise<int> &tmp, int index){
tmp.set_value ( index);
return ++index ;
}
int getvalue ( std::future<int> & tmp){
cout << tmp.get() << endl ;
return 0;
}
调用:
std::promise<int> ptr1;
std::thread m_thread1(&testPromiss,std::ref(ptr1),5);
std::future<int> result = ptr1.get_future();
std::thread m_thead2(&getvalue, std::ref(result));
m_thead1.join();
m_thead2.join();