[英]Is there a way to use std::async with std::experimental::future?
Note: Below is illegal even in C++17! 注意:即使在C ++ 17中,以下内容也是非法的!
#include <thread>
#include <future>
#include <experimental/future>
using namespace std;
int step1(experimental::future<int>)
{
return {};
}
int step2(experimental::future<int>)
{
return {};
}
int step3(experimental::future<int>)
{
return {};
}
int main()
{
return async([](){ return {}; })
.then(step1)
.then(step2)
.then(step3)
.get();
}
C++1z provides two types of future
: C ++ 1z提供了两种类型的
future
:
std::future
std:experimental::future
However, std::async
returns std::future
only, so the code above is illegal. 但是,
std::async
仅返回std::future
,因此上面的代码是非法的。 If std::async
returns std:experimental::future
, then it would be ok. 如果
std::async
返回std:experimental::future
,那就没关系。
My question is: 我的问题是:
Is there a way to use std::async
with std::experimental::future
that makes the code above legal under C++1z? 有没有办法在
std::experimental::future
中使用std::async
,使得代码在C ++ 1z下面合法?
Is there a way to use
std::async
withstd::experimental::future
that makes the code above legal under C++1z?有没有办法在
std::experimental::future
中使用std::async
,使得代码在C ++ 1z下面合法?
Nope. 不。
std::async
returns a std::future<T>
which, despite the name, is an entirely unrelated type to std::experimental::future<T>
. std::async
返回一个std::future<T>
,尽管名称是std::experimental::future<T>
,但它是一个完全不相关的类型。
You would have to write your own version of async
that gives you the new kind of future
. 您必须编写自己的
async
版本,为您提供新的future
。 A simplified version would be something like: 简化版本将是这样的:
template <class F, class... Args,
class R = std::invoke_result_t<std::decay_t<F>, std::decay_t<Args>...>>
std::experimental::future<R> new_async(F&& f, Args&&... args)
{
std::experimental::promise<R> p;
auto fut = p.get_future();
std::thread thread([p=std::move(p), f=std::forward<F>(f),
args=std::tuple<std::decay_t<Args>...>(std::forward<Args>(args)...)] () mutable
{
try
{
if constexpr(std::is_void_v<R>)
{
std::apply(std::move(f), std::move(args));
p.set_value();
}
else
{
p.set_value(std::apply(std::move(f), std::move(args)));
}
}
catch(...)
{
p.set_exception(std::current_exception());
}
});
thread.detach();
return fut;
}
That doesn't support other launch policies like async
does, but it's just a start. 这不支持像
async
这样的其他启动策略,但它只是一个开始。
It seems like std::experimental::future
has the same constructors as std::future
, so it should be possible to construct an std::experimental::future
from an std::future
. 它看起来像
std::experimental::future
具有相同的构造为std::future
,所以它应该是可以构建一个std::experimental::future
从std::future
。 However, as pointed out by ildjarn it actually isn't according to the latest draft , so there seems to be no way to do this until the TS changes accordingly. 然而,正如ildjarn所指出的那样 ,它实际上并不是根据最新的草案 ,所以在TS相应改变之前似乎没有办法做到这一点。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.