[英]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]按值捕獲this指針
[&]通過引用捕獲lambda體中使用的所有自動變量
[=]按值捕獲lambda正文中使用的所有自動變量
[]什么也沒捕捉到
這意味着只捕獲lambda體中使用的自動(范圍 - 生命周期)變量。
我不明白為什么用[&]
捕獲所有東西比單個捕獲更昂貴,但明確列出捕獲的一個優點是沒有機會捕獲你沒想到的東西。
另一方面,用[=]
捕獲可能會證明是昂貴的,因為它會復制一切。 也許這就是你的同事所指的。
這最終會抓住rect並逐個引用,並且還允許您訪問它,但它實際捕獲了多少?
使用[&]
捕獲時,它會捕獲lambda正文中具有自動存儲持續時間且使用頻率的所有變量。
這是一個例子:
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
}
如果您知道只捕獲一個變量,則不需要按值/引用捕獲所有內容。
但另一方面,如果你知道你將捕獲一些變量,用[&]
或[=]
捕獲它們比輸入它們更容易。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.