在下面的示例中,在捕获列表中使用[this]与在捕获列表中使用capture-by-reference [&]之间的区别是什么,如图所示?我试过了两个,他们产生了相同的输出。
#include <iostream>
class Test {
public:
int x = 2;
void test1(void) { std::cout << "test1" << std::endl; };
void test_lambda(void) {
auto lambda = [&] () {
std::cout << "x: " << x << " y: " << y << " z: " << z << std::endl;
this->test1();
};
lambda();
}
protected:
int y = 3;
private:
int z = 4;
};
int main() {
Test t;
t.test_lambda();
}
在C ++编程语言中,Stroustrop说:
Members are always captured by reference. That is, [this] implies that members are accessed through this rather than copied into the lambda.
这似乎意味着他们可能意味着同样的事情。如果情况确实如此,为什么我们需要[这]?
答案 0 :(得分:3)
根据cppreference:
[&amp;]通过引用捕获lambda体中使用的所有自动变量,如果存在,则通过引用捕获当前对象
而使用[this]将仅捕获this
指针。
当您在范围内有自动变量时,这会有所不同,例如:
struct Test {
void run() {
int y = 2;
// all automatic variables are accessible, both local and members
auto l1 = [&](){ cout << x << " " << y << endl; };
l1();
// y is not accessible, x is only because it's a member
auto l2 = [this]() { cout << this->x << endl; };
l2();
}
int x = 1;
};
int main() {
Test t;
t.run();
}
那么,为什么我们需要呢?
允许捕获[this]与允许捕获任何其他指针相同。
为什么不一直捕获所有自动变量?有几个原因,包括:
注意:使用&amp;捕获所有自动变量不会引入额外的性能成本,因为编译器只传递我们在lambda中使用的变量。
答案 1 :(得分:1)
&
通过引用捕获范围内的所有变量。考虑一下:
void test_lambda(void) {
int dummy = 42; // capture dummy ?!?
auto lambda = [&] () { // yes
std::cout << "x: " << x << " y: " << y << " z: " << z << std::endl;
this->test1();
std::cout << dummy; // ok here
};
lambda();
}
[this]
不会像[&]
那样捕获局部变量。
答案 2 :(得分:1)
捕获成员的唯一方法是捕获this
:
[this](){ member = 42; }
[=](){ member = 42;}
[&](){ member = 42; }
以下是非法的
[&member](){ member = 42; } // illegal
[member](){ std::cout << member; } // illegal
。然后,根据您打算表达捕获的限制,您可以选择是否明确,避免reference
捕获(以避免可能的悬空引用)......
答案 3 :(得分:0)
使用if (migrationBuilder.ActiveProvider == "Microsoft.EntityFrameworkCore.SqlServer")
{
// TODO
}
else if (migrationBuilder.ActiveProvider == "Microsoft.EntityFrameworkCore.Sqlite")
{
// TODO
}
只会捕获[this]
,而this
会从封闭范围内捕获[&]
和所有本地变量。
this
如果您的闭包将在封闭范围之外调用,您可以使用struct example {
int foo;
example() {
int bar;
[this]() {
foo = {};
bar = {}; // error: 'bar' is not captured
}();
[&]() {
foo = {};
bar = {};
}();
}
};
,就像成员函数一样,因为所有局部变量都将被销毁。
[this]
如果你的闭包将在封闭范围内调用,你可以使用struct example {
int value = 42;
example() {
frobnicate = [this]() {
std::cout << value << std::endl;
};
}
std::function<void ()> frobnicate;
};
example x;
x.frobnicate();
,就像一段本地代码一样,因为局部变量仍然存在。
[&]