Il comportamento del seguente codice è ben definito?Riferimento di associazione a un oggetto prima della costruzione
struct X { int i; }; // trivial
struct Y : X { Y(){} }; // non-trivial
extern X xobj;
int& r1 = xobj.i; // #1
X xobj;
extern Y yobj;
Y& r2 = yobj; // #2
// int& r3 = yobj.i; // #3 - this is UB according to the standard
Y yobj;
Questo codice si ispira l'esempio nello standard C++, cioè elaborare N4140 [class.cdtor]/1.
Questo è ciò che il paragrafo recita:
Per un oggetto con un costruttore non banale, con riferimento a qualsiasi classe membro o base non statica dell'oggetto prima del costruttore comincia risultati di esecuzione in un comportamento indefinito. Per un oggetto con un distruttore non banale , facendo riferimento a qualsiasi membro non statico o classe base dell'oggetto dopo che il distruttore ha terminato i risultati di esecuzione in un comportamento non definito.
Segue un esempio, che mostra come puntatori possono e non possono essere vincolati agli oggetti.
Così intuitivamente sembra che #1
e #2
sono ben definiti, mentre #3
invoca UB se non commentata, ma, in primo luogo, gli esempi non sono normative, secondo, non c'è alcuna menzione di riferimenti nella esempio, e il terzo e il più importante , il paragrafo precedente non implica che altrimenti il comportamento è ben definito. O lo fa? O forse c'è un'altra citazione rilevante nello standard che mi è sfuggita?
Edit: La risposta può (forse) essere sì se gli oggetti hanno una durata di archiviazione statica, ma possono essere anche locale, ad esempio:
struct A { A(){} };
struct B { B(A&){} };
struct C {
B b;
A a;
C() : b(a) {}
};
int main() {
C c;
}
In realtà questo è stato l'ispirazione iniziale per questa domanda, vedi Circular dependency in constructor initialization list
"fare riferimento a qualsiasi membro non statico [...] comporta un comportamento non definito" - il riferimento è esattamente ciò che fa un riferimento (da cui il nome). – molbdnilo
@molbdnilo Lo capisco, ma non spiega cosa succede * altrimenti * (ad esempio, riferendosi a ... prima che il costruttore inizi per la classe con un costruttore banale), questo è il punto della domanda. –
"riferirsi ad esso" significa menzionarlo (è la parola inglese "riferirsi"). –