C ++ lambda两个复制构造函数调用

时间:2015-12-01 13:11:58

标签: c++ c++11 visual-c++ lambda copy-constructor

我有以下代码段。

#include <iostream>
#include <functional>
using namespace std;

struct A
{
    A() { cout << "A "; data = 1; }
    A(const A& a) { cout << "cA "; data = a.data; }
    ~A() { cout << " dA"; }
    int data;
};

void f(A& a, function<void(A)> f)
{
    cout << "(";
    f(a);
    cout << ")";
}

int main()
{
    A temp;
    auto fun = [](A a) {cout << a.data;};
    f(temp, fun);
}

输出结果为:

  

A(cA cA 1 dA dA)dA

为什么temp被复制了两次?

我正在使用Visual C ++(vc140)。

1 个答案:

答案 0 :(得分:13)

function<void(A)>有一个带有此签名的函数调用运算符:operator()(A),即它按值获取其参数,因此调用f(a)会复制。

lambda也通过值获取其参数,因此当在function<void(A)>调用运算符中调用它时,会生成另一个副本。

如果为A定义移动构造函数,您应该看到初始化lambda参数(来自function创建的第一个副本)可以是移动而不是副本,但仅限于type有一个move构造函数。否则必须复制。

或者,如果使用std::function<void(const A&)>,则调用运算符将​​通过引用而不是值来获取其参数,因此只创建了一个副本,以初始化lambda的参数。