Ich versuche, die Konsistenz in den Fehler zu verstehen, die in diesem Programm geworfen wird:Pointer-to-Mitglied Verwirrung
#include <iostream>
class A{
public:
void test();
int x = 10;
};
void A::test(){
std::cout << x << std::endl; //(1)
std::cout << A::x << std::endl; //(2)
int* p = &x;
//int* q = &A::x; //error: cannot convert 'int A::*' to 'int*' in initialization| //(3)
}
int main(){
const int A::* a = &A::x; //(4)
A b;
b.test();
}
Der Ausgang ist 10 10
. I markierte 4 Punkte des Programms, aber (3) ist meine größte Sorge:
x
wird normalerweise aus dem Innern einer Elementfunktion geholt.x
des Objekts wird mit dem Bereichsoperator abgerufen und ein Lvalue zum Objektx
wird zurückgegeben.A::x
Da lieferte eineint
lvalue in (2), warum dann nicht&A::x
Rückkehr nichtint*
sondernint A::*
zurückkehrt? Der Bereichsoperator hat sogar Vorrang vor dem Operator&
, so dassA::x
zuerst ausgeführt werden sollte, bevor der Wertint
Lvalue zurückgegeben wird, bevor die Adresse übernommen wird. d. h. das sollte genauso sein wie&(A::x)
sicher? (Das Hinzufügen von Klammern funktioniert übrigens übrigens).- Ein wenig anders hier natürlich, der Geltungsbereich Operator bezieht sich auf ein Klassenmitglied, aber ohne Objekt, auf das verwiesen wird.
Warum genau funktioniert A::x
nicht zurück, die Adresse des Objekts x
sondern gibt die Adresse des Mitglieds, Vorrang von ::
vor &
ignorieren?
Ich denke, wenn es anders klappt, würde es zu mehr Verwirrung führen. Die gleiche Folge von Bezeichnern und Operatoren, die genau die gleichen Typen und Mitglieder referenzieren, also zwei verschiedene Dinge, je nach Umfang: Klingt nach Ärger für mich. –
@ John Sensebe definitiv. Ich habe ursprünglich "Quirk" geschrieben, aber das ist in der Tat eine sehr vernünftige Wahl, obwohl es auf den ersten Blick seltsam erscheinen kann. – Quentin