La dirección de i
nunca va a cambiar en main()
, pero el valor que contiene. Está tomando la referencia de una variable local y usándola después de que la referencia haya caído fuera del alcance. (Advertencia de lenguaje impreciso) El valor 6
está en la pila. Como no hizo nada con la pila después de poner allí el 6
, la referencia a ella aún contendrá el mismo valor. Entonces, como otros han dicho, tuvieron suerte.
para ver cuán afortunada, intente ejecutar el código que utiliza la pila después de llamar foo()
:
#include <iostream>
#include <ctime>
#include <numeric>
int& foo()
{
int i = 6;
std::cout << &i << " = " << i << std::endl; //Prints the address of i before return
return i;
}
long post_foo(int f)
{
srand((unsigned)time(0));
long vals[10] = {0};
size_t num_vals = sizeof(vals)/sizeof(vals[0]);
for(size_t i = 0; i < num_vals; ++i)
{
int r = (rand()%2)+1;
vals[i] = (i+f)*r;
}
long accum = std::accumulate(vals, &vals[num_vals], 0);
return accum * 2;
}
int main()
{
int &i = foo();
// std::cout << "post_foo() = " << post_foo(i) << std::endl;
std::cout << &i << " = " << i << std::endl;
}
Cuando me encontré con esto con el post_foo()
llamada comentado, 6
todavía estaba en la pila y la salida era:
002CF6C8 = 6
002CF6C8 = 6
... pero cuando un-comentó la llamada a post_foo()
y corrió otra vez, 6
había ido de largo:
001FFD38 = 6
post_foo() = 310
001FFD38 = 258923464
Tienes suerte. No lo hagas –
Puede encontrar esto útil: http://stackoverflow.com/questions/6441218/can-a-local-variables-memory-be-accessed-outside-its-scope – letsc
Creo que algo de suerte está en el hecho de que es inalterado en foo() (que permite a los compiladores colocar en texto o en algún lugar de larga vida en lugar de pila) – mho