funciones examples c++ c++11 lambda

funciones - lambda examples c++



C++ Lambdas: diferencia entre "mutable" y captura por referencia (1)

En C ++ puedes declarar lambdas por ejemplo así:

int x = 5; auto a = [=]() mutable { ++x; std::cout << x << ''/n''; }; auto b = [&]() { ++x; std::cout << x << ''/n''; };

Ambos me permiten modificar x , ¿cuál es la diferencia?


Que esta pasando

El primero solo modificará su propia copia de x y dejará el exterior x sin cambios. El segundo modificará el exterior x .

Agregue una declaración de impresión después de probar cada uno:

a(); std::cout << x << "----/n"; b(); std::cout << x << ''/n'';

Se espera que esto se imprima:

6 5 ---- 6 6

Por qué

Puede ser útil considerar que las [...] expressions provide a concise way to create simple function objects lambda [...] expressions provide a concise way to create simple function objects (vea [expr.prim.lambda] del Estándar).

Tienen un operador de llamada de función pública [...] en línea que se declara como una función const , [...] pero solo si y solo si la cláusula parameter-declaration-clause lambdaexpression no es seguida por mutable (texto en cursiva = citas del estándar).

Puedes pensar como si

int x = 5; auto a = [=]() mutable { ++x; std::cout << x << ''/n''; }; ==> int x = 5; class __lambda_a { int x; public: __lambda_a () : x($lookup-one-outer$::x) {} inline void operator() { ++x; std::cout << x << ''/n''; } } a;

y

auto b = [&]() { ++x; std::cout << x << ''/n''; }; ==> int x = 5; class __lambda_b { int &x; public: __lambda_b() : x($lookup-one-outer$::x) {} inline void operator() const { ++x; std::cout << x << ''/n''; } // ^^^^^ } b;

P: Pero si es una función const , ¿por qué aún puedo cambiar x ?

A: solo estás cambiando el exterior x . La propia x lambda es una referencia, y la operación ++x no modifica la referencia , sino el valor referido .

Esto funciona porque en C ++, la constness de un puntero / referencia no cambia la constness del pointee / referencee visto a través de él.