C++:std :: thread的简单返回值?

sho*_*osh 35 c++ multithreading

使用win32线程,我有直接向前GetExitCodeThread()提供线程函数返回的值.我正在寻找类似的东西std::thread(或提升线程)
据我所知,这可以通过期货完成,但究竟如何呢?

Ale*_*x B 61

请参阅有关C++ 11期货的视频教程.

明确与线程和期货:

#include <thread>
#include <future>

void func(std::promise<int> && p) {
    p.set_value(1);
}

std::promise<int> p;
auto f = p.get_future();
std::thread t(&func, std::move(p));
t.join();
int i = f.get();
Run Code Online (Sandbox Code Playgroud)

或者std::async(线程和期货的更高级别包装器):

#include <thread>
#include <future>
int func() { return 1; }
std::future<int> ret = std::async(&func);
int i = ret.get();
Run Code Online (Sandbox Code Playgroud)

我无法评论它是否适用于所有平台(它似乎适用于Linux,但不适用于Mac OSX和GCC 4.6.1).

  • @kevinarpe [我在 5 年前写了这个,而且我多年来没有写过任何 C++,所以我猜过去我在这里试图做什么......] 基本上承诺值是在另一个线程中设置的。Promise 是不可复制的,所以你不能通过值传递它(它首先是可复制的,这是没有意义的)。并且因为堆栈值可能超出范围,您也不能通过引用传递它。因此,您需要将对象的所有权转移给线程 = 移动它 + 必须将其作为右值引用传递。 (5认同)
  • @sehe通常这些沙盒环境不允许启动线程. (2认同)

seh*_*ehe 32

我会说:

#include <thread>
#include <future>

int simplefunc(std::string a)
{ 
    return a.size();
}

int main()
{
      auto future = std::async(simplefunc, "hello world");
      int simple = future.get();

      return simple;
}
Run Code Online (Sandbox Code Playgroud)

请注意,异步甚至会传播从线程函数抛出的任何异常

  • 好的!谢谢你!C++规则! (2认同)
  • 顺便说一句,许多问题的存在并不意味着有什么东西得到了很好的支持.它主要意味着某些东西是学习曲线的内在障碍.内在的复杂性很好,如果你没有直觉地想到它,那就太惊讶了.学习让惊喜消失了.就个人而言,我认为C#的`Task <T>`with async + await胜过C++语言级别的支持(好吧,现在).我认为你基本上看到编程语言的演变是颠倒的. (2认同)

Dak*_*ksh 5

使用 C++11 线程,无法获取线程退出时的返回值,而以前的情况是这样的pthread_exit(...)

您需要使用C++11Future<>来获取返回值。Future 是使用模板化参数创建的,其中模板采用返回值(内置用户定义类型)。

您可以使用函数在另一个线程中获取值future<..>::get(..)

using 的好处之一future<..>是您可以检查返回值的有效性,即如果它已经被占用,您可以get()通过使用函数检查有效性来避免意外调用future<..>::isValid(...)

以下是编写代码的方法。

#include <iostream>
#include <future>
using namespace std;
auto retFn() {
    return 100;
}
int main() {
    future<int> fp = async(launch::async, retFn);
    if(fp.valid())
       cout<<"Return value from async thread is => "<<fp.get()<<endl;
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

launch::deferred还应该注意的是,我们可以通过使用选项 as来让未来在同一线程上运行

 future<int> fp = async(launch::deferred, retFn);
Run Code Online (Sandbox Code Playgroud)