C++ boost::future和continuations-值集,但future仍然阻塞
我正试图使下面的继续工作正常-但是C++ boost::future和continuations-值集,但future仍然阻塞,c++,boost,future,continuations,C++,Boost,Future,Continuations,我正试图使下面的继续工作正常-但是f.get()blocks。怎么了 #include <iostream> #define BOOST_THREAD_PROVIDES_FUTURE #define BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION #include <boost/thread/future.hpp> struct Foo { boost::future<int> start() { r
f.get()
blocks。怎么了
#include <iostream>
#define BOOST_THREAD_PROVIDES_FUTURE
#define BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
#include <boost/thread/future.hpp>
struct Foo {
boost::future<int> start() {
return p.get_future();
}
void finish() {
p.set_value(23);
}
boost::promise<int> p;
};
int main () {
Foo foo;
foo.start().then([](boost::future<int> f) {
std::cout << "done:" << std::endl;
std::cout << f.get() << std::endl;
});
foo.finish();
}
更新:以下代码更改将使示例正常工作-但为什么?因为无论如何都不使用f2。又困惑了
boost::future<void> f2 = foo.start().then([](boost::future<int> f) {
std::cout << "done:" << std::endl;
std::cout << f.get() << std::endl;
});
这也是:
boost::future<int> start() {
boost::future<int> f = p.get_future();
f.set_deferred();
return f;
}
boost::future start(){
boost::future f=p.get_future();
f、 set_deferred();
返回f;
}
问题是,你沉着冷静的未来没有得到保障。事实上,它是一个临时语句,并且在语句(带有.then()
)结束时会被销毁
修复它:
int main () {
Foo foo;
auto f1 = foo.start();
auto f2 = f1.then([](boost::future<int> f) {
std::cout << "done:" << std::endl;
std::cout << f.get() << std::endl;
});
foo.finish();
f2.get();
}
查看它
如果在
foo.finish()之前移动f2.get()
,它将再次死锁。Hah。我只是回答。您的变量f2
会延长未来的生存期,直到/在/承诺准备就绪。这是一个变化。因此,是的,f2
被隐式使用(如果只用于析构函数的话)。有道理。然而,与此同时,我发现了关于“发布政策”的问题。因为实际上我不需要f2(如果我愿意,那么我需要保留它),所以使用启动策略似乎更合适?请参阅Q中的“更新2”。如果您的意思是缺少线程并发性,那么是的,这解释了死锁。然而,延迟
只是意味着任务没有“急切地”安排,最重要的更改是在线程上运行它。相反,我希望你能。只要使用deferred
标志,就可以双重确保不会触发任何任务,因为您不会等待第二个未来。FWIW,我根本不想使用线程。我希望在单个(主)线程上有异步控制流。就像JavaScript承诺或扭曲的尊重一样。我还在C++中学习这些东西……奥伯斯特我可以衷心推荐Boost Asio吗?特别是看协程,但一般来说,如果您正在寻找反应器式并发(在单个线程或多个线程上),Boost Asio是您的下一个选择stop@oberstet我刚刚用Boost Asio编写了一个简单的http示例客户机,也许您会认识到reactor风格。这不是一个非常有说服力的异步示例,但它确实会在Eccleston的截止时间计时器上取消:)
boost::future<int> start() {
boost::future<int> f = p.get_future();
f.set_deferred();
return f;
}
int main () {
Foo foo;
auto f1 = foo.start();
auto f2 = f1.then([](boost::future<int> f) {
std::cout << "done:" << std::endl;
std::cout << f.get() << std::endl;
});
foo.finish();
f2.get();
}
done:
23