C++11 Lambda Capture

· 442 words · 1 minute read

好记性不如烂笔头,内容来自cppreference.com.

语法 🔗

c++11 的 lambda capture 大概有如下语法:

identifier (1)
identifier ... (2)
identifier initializer (3) (since C++14)
& identifier (4)
& identifier ... (5)
& identifier initializer (6) (since C++14)
this (7)
* this (8) (since C++17)
... identifier initializer (9) (since C++20)
& ... identifier initializer (10) (since C++20)

其中,

  • (1) simple by-copy capture
  • (2) simple by-copy capture that is a pack expansion
  • (3) by-copy capture with an initializer
  • (4) simple by-reference capture
  • (5) simple by-reference capture that is a pack expansion
  • (6) by-reference capture with an initializer
  • (7) simple by-reference capture of the current object
  • (8) simple by-copy capture of the current object
  • (9) by-copy capture with an initializer that is a pack expansion
  • (10) by-reference capture with an initializer that is a pack expansion

如果某个 lambda 的 capture-default 是 &, 则后续的 simple capture 不能再以 & 打头 – 没啥意义。

示例1 🔗

struct S2 { void f(int i); };
void S2::f(int i)
{
    [&] {};          // OK: by-reference capture default
    [&, i] {};       // OK: by-reference capture, except i is captured by copy
    [&, &i] {};      // Error: by-reference capture when by-reference is the default
    [&, this] {};    // OK, equivalent to [&]
    [&, this, i] {}; // OK, equivalent to [&, i]
}

同理, 如果某个 lambda 的 capture-default 是 =, 则后续的 simple capture 必须以 & 打头。

示例2 🔗

struct S2 { void f(int i); };
void S2::f(int i)
{
    [=] {};        // OK: by-copy capture default
    [=, &i] {};    // OK: by-copy capture, except i is captured by reference
    [=, *this] {}; // until C++17: Error: invalid syntax
                   // since C++17: OK: captures the enclosing S2 by copy
    [=, this] {};  // until C++20: Error: this when = is the default
                   // since C++20: OK, same as [=]
}

示例3 🔗

capture 只能出现一次,且不能和参数重名。

struct S2 { void f(int i); };
void S2::f(int i)
{
    [i, i] {};        // Error: i repeated
    [this, *this] {}; // Error: "this" repeated (C++17)

    [i] (int i) {};   // Error: parameter and capture have the same name
}
c++
comments powered by Disqus