C++11 lambda捕获实际捕获了多少
How much does a C++11 lambda capture actually capture?
我在多个示例中看到,可以使用单个字符捕获多个变量,如下所示:
Rect rect;
Point point;
auto someLambda = [&](const SomeType& var)
{
if (rect.Contains(point))
{
var.Something();
}
this->MemberFunction();
};
这最终会通过引用获取rect
和point
,并允许您访问this
,但它实际捕获了多少?它是只捕获它需要的变量,还是捕获当前范围内的所有变量?
我在其他示例中看到,您也可以指定要捕获的单个变量,如下所示:
Rect rect;
Point point;
auto someLambda = [this, &rect, &point](const SomeType& var)
{
if (rect.Contains(point))
{
var.Something();
}
this->MemberFunction();
};
这样或那样做有什么好处吗?我的同事曾经提到,使用"捕获所有"[&]
版本更贵,但我找不到任何文档来支持这一点。我只是想确定一下,这样我就不会让代码变得比它需要的更复杂,也不会做我不应该做的昂贵的事情。
根据http://en.cppreference.com/w/cpp/language/lambda,捕获列表(方括号中的部分)为:
以逗号分隔的零个或多个捕获的列表,可选地以开头具有捕获默认值。捕获列表可以按如下方式传递[…]:
[a,&b]其中a是通过值捕获的,b是通过引用捕获的。
[this]通过值捕获该指针
[&]捕获的正文中使用的所有自动变量odrλ参考
[=]捕获所有使用的自动变量odr在lambda的主体中按值
[]未捕获任何
这意味着只有lambda主体中使用的自动(作用域生存期)变量才会被捕获。
我不明白为什么用[&]
捕获所有内容会比单个捕获更昂贵,但明确列出捕获的一个好处是,没有机会捕获到你意想不到的东西。
另一方面,使用[=]
进行捕获可能代价高昂,因为它可以复制所有内容。也许这就是你的同事所指的。
这最终通过引用获取rect和point,也让您可以访问它,但它实际捕获了多少?
当您使用[&]
捕获时,它会捕获lambda主体中具有自动存储持续时间并使用odr的所有变量。
这里有一个例子:
int main()
{
int num = 50;
[&] { std::cout << num << 'n'; }(); // num captured by reference
[=] { std::cout << num << 'n'; }(); // num captured by value
[&num] { std::cout << num << 'n'; }(); // by reference
[num] { std::cout << num << 'n'; }(); // by value
}
如果您知道只捕获一个变量,则不需要按值/引用捕获所有变量。
但另一方面,如果您知道您将捕获一些变量,那么使用[&]
或[=]
捕获它们比将它们全部键入更容易。
- 复制列表初始化的隐式转换的等级是多少
- while循环中while循环的时间复杂度是多少
- MSVC是否支持C++11样式的属性而不是__declspec
- 创建LinkedList退出,返回代码为-11(SIGSEGV)
- 我可以将一个用clang c++11编译的对象与另一个用c++17编译的对象链接起来吗
- 继承:构造函数,初始化C++11中基类的类C数组成员
- 如何检查一个c++字符串中有多少相同的字符/数字
- C++有多少类型的循环
- 如何将模板转换为C++11之前的模板
- 求出有多少个数字是完美平方,而sqrt()是L,R范围内的素数
- c++11评估顺序(未定义的行为)
- C++中的VLA,扩展名为std=C++11
- 代码在我的计算机上运行良好,但是在将其提交给coursera时遇到未知的信号11问题
- "类模板示例<int>;"语句对 C++11 是什么意思?
- this_thread::sleep_for和计时时钟之间的关系是否由C++11标准指定
- 如何使用lock_guard在c++11中实现scoped_lock功能
- 在条件变量中触发错误信号的频率是多少
- 实际上,C++11 中 std::atomic 的内存占用量是多少?
- C++11 lambda捕获实际捕获了多少
- 使用 C++11 自动关键字多少钱才算太多