从通用lambda创建线程,引用作为通用参数

时间:2016-04-15 17:24:49

标签: c++ lambda c++14

如何使用定义为引用的自动参数的通用lambda创建线程?

例如,实现概念上等同于此的东西的正确方法是什么:

int vi = 0;
auto lambda = [](auto &v) {};
auto t = std::thread(lambda, std::ref(vi)); 

gcc-5.3由于缺少类型而抱怨:

/opt/gcc/el6/gcc-5.3.0/include/c++/5.3.0/functional: In instantiation of ‘struct std::_Bind_simple<main()::<lambda(auto:2&)>(std::reference_wrapper<int>)>’:
/opt/gcc/el6/gcc-5.3.0/include/c++/5.3.0/thread:137:59:   required from ‘std::thread::thread(_Callable&&, _Args&& ...) [with _Callable = main()::<lambda(auto:2&)>&; _Args = {std::reference_wrapper<int>}]’
testLambdaCapture.cpp:52:41:   required from here
/opt/gcc/el6/gcc-5.3.0/include/c++/5.3.0/functional:1505:61: error: no type named ‘type’ in ‘class std::result_of<main()::<lambda(auto:2&)>(std::reference_wrapper<int>)>’
   typedef typename result_of<_Callable(_Args...)>::type result_type;
                                                         ^
/opt/gcc/el6/gcc-5.3.0/include/c++/5.3.0/functional:1526:9: error: no type named ‘type’ in ‘class std::result_of<main()::<lambda(auto:2&)>(std::reference_wrapper<int>)>’
         _M_invoke(_Index_tuple<_Indices...>)
         ^

作为一个附带问题,为什么当泛型参数按照这样的值传递时它才起作用:

auto lambda = [](auto v) {};
auto t = std::thread(lambda, vi);

2 个答案:

答案 0 :(得分:2)

固定:

#include <thread>

int vi = 0;
auto lambda = [](auto &&v) {};
auto t = std::thread(lambda, std::ref(vi)); 

// this works too
auto rv = std::ref(vi);
auto t2 = std::thread(lambda, rv); 

在这种情况下,auto&amp;&amp;被推断为好像它是一个模板参数。因此,实例化期间的实际类型可以是const T&T&&

答案 1 :(得分:1)

问题是它试图从类型auto&的右值中推导出std::reference_wrapper<int>而没有这样做,因为不能从rvalues中推导出非常量左值引用。只有当目标函数具有对已知类型的引用(意味着没有推论,并且reference_wrapper的转换运算符适用)或非引用类型(意味着不需要转换)时,它才有效。