future 是检查单个线程完成情况的安全方法吗?

nok*_*oko 1 c++ multithreading boost thread-safety

我一直在研究 Boost 的 future,想知道它们是否是检查单个线程是否已完成的可接受且安全的方法。

我以前从未使用过它们,所以我编写的大部分代码都是基于Boost 的同步文档

#include <iostream>
#include <boost/thread.hpp>
#include <boost/thread/future.hpp>

int calculate_the_answer_to_life_the_universe_and_everything()
{
    boost::this_thread::sleep(boost::posix_time::seconds(10));
    return 42;
}

int main()
{
    boost::packaged_task<int> task(calculate_the_answer_to_life_the_universe_and_everything);
    boost::unique_future<int> f(task.get_future());

    boost::thread th(boost::move(task));

    while(!f.is_ready())
    {
        std::cout << "waiting!" << std::endl;
        boost::this_thread::sleep(boost::posix_time::seconds(1));
    }

    std::cout << f.get() << std::endl;

    th.join();
}
Run Code Online (Sandbox Code Playgroud)

这似乎在等待calculate_the_answer_to_life_the_universe_and_everything()线程返回42。这可能会出现问题吗?

谢谢!

Jon*_*ely 5

是的,以这种方式使用期货是安全的,并且代码(快速浏览)是安全且正确的。

还有其他方法可以完成相同的操作(例如使用atomic_flag、 或互斥锁保护的数据或许多其他方法),但您的代码是执行此操作的有效方法。

注意,您可以使用,f.is_ready()而不是,一旦结果准备好,它就会唤醒。它直接等待未来,而不是检查未来,然后使用单独的机制等待,然后检查,然后使用单独的机制等待等等。this_thread::sleep(seconds(1))f.wait_for(seconds(1))

你可以使用来代替packaged_taskand 。threadasync

使用 C++11 名称而不是 boost ...

int main()
{
    auto f =  std::async(std::launch::async, calculate_the_answer_to_life_the_universe_and_everything);

    while(f.wait_for(std::chrono::seconds(1)) == std::future_status::timeout)
        std::cout << "waiting!" << std::endl;

    std::cout << f.get() << std::endl;
}
Run Code Online (Sandbox Code Playgroud)