【发布时间】:2015-11-05 20:23:05
【问题描述】:
我需要通过 MyClass2 将用户定义的 lambda 传递给 MyClass1。我想确保只有一个动作,没有副本。下面的代码是否实现了这一点?有没有更好的方法来做到这一点(比如使用编译器完成的隐式移动)?
注意:我可以控制 MyClass1 和 MyClass2
#include <functional>
using MyFunction = std::function<int(int)>;
class MyClass1 {
public:
MyClass1(const MyFunction& func): mFunc(std::move(func)) {}
private:
MyFunction mFunc;
};
class MyClass2 {
public:
MyClass1* getClass1(const MyFunction& func) {
return new MyClass1(func);
}
};
int main() {
MyClass2 cl2;
const auto& f = [] (int i) { return i; };
MyClass1* cl1 = cl2.getClass1(f);
}
【问题讨论】:
-
你不能移动一个常量引用
-
@bolov 但它似乎编译得很好。
-
你可以
std::moveconst,但它通常什么都不做 除了使用时的副本。它是const,你不能剥去它的内脏,std::move只是将某些东西标记为“安全地剥去内脏”。额外的移动很便宜:在你写的任何地方用MyFunction替换const MyFunction&。将MyClass1(func)替换为MyClass1(std::move(func))。 -
@Lol4t0
std::function要求可调用它的包装是可复制构造的,你的不是因为只有移动类型。捕获可复制类型的 Lambda 是可复制的,可以存储在std::function -
@vikky.rk 摆脱了
f上的const&和move无论如何。您的代码(如上所述)已经复制了f,因为f不是std::function,它是一个lambda。 Lambda 不是std::functions,std::functions 不是 lambda。move将其放入std::function中将消除您的std::function<?> const&案例和我的std::function<?>案例中的副本(并用移动替换它)。