Todos sabemos que este tipo de cosas son válidos en C++:referencia constante a la rareza temporal
const T &x = T();
mientras:
T &x = T();
no lo es.
En a recent question la conversación condujo a esta regla. El OP había publicado un código que evoca claramente a UB. Pero tendría que esperar una versión modificada de que funcione (Esta es la versión modificada):
#include <iostream>
using namespace std;
class A {
public:
A(int k) { _k = k; };
int get() const { return _k; };
int _k;
};
class B {
public:
B(const A& a) : _a(a) {}
void b() { cout << _a.get(); }
const A& _a;
};
B* f() {
return new B(A(10));
}
int main() {
f()->b();
}
Esto imprime la basura en algunas máquinas, 10 en los demás ... suena como UB me :-). Pero luego pensé, bueno, A
es básicamente una glorificada int
, todo lo que hace es inicializar una y leerla. ¿Por qué no acaba de llamar A
un int
y ver lo que sucede:
#include <iostream>
using namespace std;
typedef int A;
class B {
public:
B(const A& a) : _a(a) {}
void b() { cout << _a; }
const A& _a;
};
B* f() {
return new B(A(10));
}
int main() {
f()->b();
}
imprime 10
cada vez. Al menos parece como la regla de referencia const está en vigor para la versión int
, pero no para la versión de clase. ¿Ambos son simplemente UB debido al uso del montón? ¿Tengo suerte con la versión int
porque la compilación vio a través de todos const
sy simplemente imprimí directamente un 10
? ¿Qué aspecto de la regla me falta?
Le sugiero que cambie "a const reference" por "a * local * const reference" para aclarar aún más las cosas;) – fredoverflow
@FredOverflow: ¿Por qué insiste en una referencia * local *? Puede declarar legalmente 'const std :: string & r =" Hello "' en el ámbito del espacio de nombres y obtener la misma extensión de por vida. – AnT
@AndreyT, ¿cómo se establece este * enlace * en qué nivel? –