【问题标题】:using std::transform for calling object's function使用 std::transform 调用对象的函数
【发布时间】:2013-08-15 19:51:21
【问题描述】:

假设我有一个 A 类对象的共享指针向量。我想为所有 A 对象收集方法 A::foo 的所有返回值,并将它们存储在某个容器中,比如另一个向量。 这可以用std::transformstd::for_eachstd::bind 或一些boost 函数来完成吗?

class A {

  public:
  string foo(int p);

};

std::vector<shared_ptr<A>> vec;

【问题讨论】:

    标签: c++ stl lambda boost-bind


    【解决方案1】:

    std::transform 可以这样做:

    std::vector<std::string> string_vec;
    const int magic_number = 42;
    std::transform(std::begin(vec),
                  std::end(vec),
                  std::back_inserter(string_vec),
                  [magic_number](std::shared_ptr<A> a){ return a->foo(magic_number); } );
    

    显然,您需要确定要将哪个int 传递给A::foo(int)

    在 C++03 中,您可以将 lambda 替换为仿函数或函数:

    struct get_foo
    {
      get_foo(int n) : n_(n) {}
      bool operator() (std::shared_ptr<A> a) const { return a->foo(n); }
    private:
      int n_;
    };
    
    const int magic_number = 42;
    std::vector<std::string> string_vec;
    std::transform(std::begin(vec),
                  std::end(vec),
                  std::back_inserter(string_vec),
                  get_foo(magic_number));
    

    【讨论】:

    • 如果您需要将多个不同的值传递给 a-&gt;foo 调用,您将需要创建一个仿函数而不是使用 lambda 函数,以便在您通过它们时存储状态。
    • 感谢您的回答。我一直在寻找不带 lambda 的旧版 c++ 的方法,这可以通过绑定和可用的 stl 函子来完成,而无需定义我们自己的自定义函子,采用 vec 的迭代器。
    • @ZacHowland 另一种选择是将值放在另一个向量中,并使用std::transform 的二元函子重载。但鉴于问题中的细节很少,我想42 是一个很好的数字。
    • @user124 当然,你可以写一个仿函数,甚至是一个简单的函数。您应该在问题中指定要从哪里获取 foo()int 值。
    • 对于争论的混淆感到抱歉。 foo 的参数在整个 vec 范围内保持不变,比如 42。A 的类型对象根据它们的状态返回不同的字符串,A 是一种基类,我们有 A 对象的向量。在搜索时,我偶然发现了在调用函数的类似场景中使用的 std::bind 和 std::transform 函数,所以想如果这也可以使用它们来完成......说一行,而不是写几行仿函数代码..但在这种情况下,std::bind 似乎没有用...
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-11-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多