rra*_*alf 6 c++ multithreading c++11
我想做的应该很容易,但我不明白......
我想要做的就是在某个特定时间点在后台启动类的成员函数.该功能的结果也应该是"外部"可用的.所以我想在构造函数中准备任务(设置future变量,...)并在稍后的某个时间启动它.
我试图结合std ::(packaged_task | async | future),但我没有让它工作.
这段代码不会编译,但我认为它显示了我想要做的事情:
class foo {
private:
// This function shall run in background as a thread
// when it gets triggered to start at some certain point
bool do_something() { return true; }
std::packaged_task<bool()> task;
std::future<bool> result;
public:
foo() :
task(do_something), // yes, that's wrong, but how to do it right?
result(task.get_future())
{
// do some initialization stuff
.....
}
~foo() {}
void start() {
// Start Task as asynchron thread
std::async as(std::launch::async, task); // Also doesn't work...
}
// This function should return the result of do_something
bool get_result() { return result.get(); }
};
Run Code Online (Sandbox Code Playgroud)
提前致谢!
And*_*owl 10
只需使用std::bind():
#include <functional> // For std::bind()
foo() :
task(std::bind(&foo::do_something, this)),
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
result(task.get_future())
{
// ...
}
Run Code Online (Sandbox Code Playgroud)
而且,你在这里做错了:
std::async as(std::launch::async, task)
// ^^
// Trying to declare a variable?
Run Code Online (Sandbox Code Playgroud)
因为你想要的是调用std::async()函数,而不是声明一个(不存在的)类型的对象std::async().因此,作为第一步,将其更改为:
std::async(std::launch::async, task)
Run Code Online (Sandbox Code Playgroud)
但请注意,这不足以使任务异步运行:由于std::async()丢弃返回的未来时的奇怪行为,您的任务将始终执行,就像您同步启动它一样 - 返回的未来对象的析构函数将阻止直到操作完成.(*)
要解决最后一个问题,您可以在result成员变量中保留返回的未来(而不是分配给构造时result返回的未来std::packaged_task::get_future()):
result = std::async(std::launch::async, task);
// ^^^^^^^^
Run Code Online (Sandbox Code Playgroud)
(*)我认为 MSVC忽略了这个规范,实际上是异步执行任务.因此,如果您正在使用VS2012,您可能不会遇到此问题.
编辑:
正如Praetorian在他的回答中正确提到的那样,上述内容仍然存在问题,因为packaged_task将在实施过程中的某个时刻尝试复制async().要解决此问题,请使用包装将task对象包装在引用包装中std::ref().
| 归档时间: |
|
| 查看次数: |
3023 次 |
| 最近记录: |