【问题标题】:Unable to bind function to std::function<void()> when passing a std::move() object as a function argument将 std::move() 对象作为函数参数传递时,无法将函数绑定到 std::function<void()>
【发布时间】:2019-01-24 02:39:38
【问题描述】:

尝试编译以下 sn-p 代码:

#include <iostream>
#include <future>
#include <functional> 

void print_num(std::promise<bool>&& result, int i )
{
    std::cout << i << " " << '\n' ;
    result.set_value(true);
}

int main()
{
   std::promise<bool> Promise0;
   std::future<bool> Result0 = Promise0.get_future();      
   std::function<void()> f_display_31337 = std::bind(print_num, std::move(Promise0), 31337);

}

得到以下错误:

在函数 'int main()' 中:15:90:错误:从 'std::_Bind_helper&&, int)、std::promise, int>::type {aka std::_Bind, int)))( std::promise&&, int)>}' 到非标量类型 'std::function' 请求

我知道这与函数参数 std::promise&& 以及对 std::move 的需求有关,但我被卡住了。

【问题讨论】:

    标签: c++11 std-function stdbind stdmove


    【解决方案1】:

    bind 返回将移动的promise(不可复制对象)作为数据成员的未指定类型的对象。 function 是 Callable 对象的包装器,function 实例的要求之一是制作存储的 Callable 的副本,在您的情况下,从 bind 返回的对象无法传递给函数,因为由于无法制作副本promise 作为数据成员。

    您应该使用auto 来推断绑定结果的类型。

    void print_num(std::promise<bool>& result, int i )
    {
        std::cout << i << " " << '\n' ;
        result.set_value(true);
    }
    
    int main()
    {
       std::promise<bool> Promise0;
       std::future<bool> Result0 = Promise0.get_future();      
    
       auto obj = std::bind(print_num, std::move(Promise0), 31337);
       obj();
    }
    

    【讨论】:

      【解决方案2】:

      也许您应该使用 move-capturing lambda 而不是 std::bind

      int main()
      {
         std::promise<bool> Promise0;
         std::future<bool> Result0 = Promise0.get_future();      
         std::function<void()> f_display_31337 =
            [Promise0 = std::move(Promise0)] mutable
            { print_num(std::move(Promise0), 31337); };
      }
      

      唯一的缺点是您需要启用c++14 才能编译此代码。

      【讨论】:

        【解决方案3】:

        如果您可以将std::promise&amp;&amp; 更改为std::promise&amp; 并将std::move 更改为std::ref

        【讨论】:

          猜你喜欢
          • 2013-12-14
          • 1970-01-01
          • 2021-03-20
          • 1970-01-01
          • 1970-01-01
          • 2016-12-29
          • 1970-01-01
          • 1970-01-01
          • 2018-04-20
          相关资源
          最近更新 更多