我刚写了一个非常大的捕获:
[this, &newIndex, &indexedDirs, &filters, &flags, &indexRecursion](){...
我将这个lambda(indexRecursion)用于带有元素元素的递归,并问自己,使用“全局”捕获[&]
是否更有效。由于我不知道捕获的实现,我需要一些解释。请带背景。
答案 0 :(得分:4)
通常你可以认为lambda与此相当:
class ANON {
int data;
public:
void operator ()(void) const {
cout << data << endl;
}
} lambda;
// auto lambda = [data]() {cout << data << endl;}
这可以让您了解如何实现捕获。捕获所有(通过复制=
或引用&
)可能只是语法糖,用于指定当前范围内捕获的所有已使用/可用变量。
但是因为......
[..]实现可以定义闭包类型与下面描述的不同,前提是这不会改变程序的可观察行为,只需更改:[..]闭包类型的大小和/或对齐方式[..]
[N4431§5.1.2/ 3]
...实现使用某种“黑魔法”来捕获所有引用lambdas并使用指向捕获的堆栈帧的指针,重写对变量的访问作为对某些偏移的访问是合法的。那个指针:
class ANON {
void * stack_frame;
public:
void operator ()(void) const {
cout << *static_cast<int *>(stack_frame + 8) << endl;
}
} lambda;
所以使用&
可能(有一天)会更有效率,但正如已经说过的那样,这是实现定义的,没有什么可以依赖的。
答案 1 :(得分:2)
内部lambdas /通常/实现为ad-hoc类,其单个实例对象在lambda定义点构造,并且暴露了稍后要调用的functor。因此,应将lambda性能与使用std::bind
将方法传递给函数进行比较。
捕获也不是神秘的实体。如果捕获是引用捕获,那么它们引用的实体在像往常一样走出范围时会被破坏,所以要注意你的lambda是否不是本地的:在它的体内它可能引用已经被破坏的对象。 / p>