examples c++ gcc lambda c++11 g++

examples - Capturar variable de referencia por copia en C++ 0x lambda



lambda examples c++ (2)

Compilado con VS 2010 da:

value capture i: 10 ir: 10 &i: 0012FE74 &ir: 0012FE78 reference capture i: 10 ir: 10 &i: 0012FF60 &ir: 0012FF60

Parece un error para mí.

Según las respuestas y los comentarios de esta pregunta , cuando una variable de referencia se captura por valor, el objeto lambda debe hacer una copia del objeto al que se hace referencia, no la referencia en sí misma. Sin embargo, GCC no parece hacer esto.

Usando la siguiente prueba:

#include <stddef.h> #include <iostream> using std::cout; using std::endl; int main(int argc, char** argv) { int i = 10; int& ir = i; [=] { cout << "value capture" << endl << "i: " << i << endl << "ir: " << ir << endl << "&i: " << &i << endl << "&ir: " << &ir << endl << endl; }(); [&] { cout << "reference capture" << endl << "i: " << i << endl << "ir: " << ir << endl << "&i: " << &i << endl << "&ir: " << &ir << endl << endl; }(); return EXIT_SUCCESS; }

La compilación con GCC 4.5.1, utilizando -std=c++0x , y en ejecución da el siguiente resultado:

value capture i: 10 ir: -226727748 &i: 0x7ffff27c68a0 &ir: 0x7ffff27c68a4 reference capture i: 10 ir: 10 &i: 0x7ffff27c68bc &ir: 0x7ffff27c68bc

Cuando se captura por copia, solo hace referencia a los datos basura. Pero hace referencia correctamente a i cuando se captura por referencia.

¿Es esto un error en GCC? Si es así, ¿alguien sabe si una versión posterior lo soluciona? ¿Cuál es el comportamiento correcto?

EDITAR

Si la primera función lambda se cambia a

[i, ir] { cout << "explicit value capture" << endl << "i: " << i << endl << "ir: " << ir << endl << "&i: " << &i << endl << "&ir: " << &ir << endl << endl; }();

entonces el resultado se ve correcto:

explicit value capture i: 10 ir: 10 &i: 0x7fff0a5b5790 &ir: 0x7fff0a5b5794

Esto se parece cada vez más a un error.


Esto acaba de arreglarse en gcc-4.7 trunk y gcc-4.6 branch. Estos deberían estar disponibles en gcc-4.7.0 (dentro de un tiempo, aún en la etapa 1) y gcc-4.6.2 (por desgracia, salió 4.6.1).

Pero el intrépido podría esperar las siguientes instantáneas u obtener una copia de subversión.

Ver pista de auditoría para más detalles.