Ich habe gelernt, dass ich niemals auf eine private Variable zugreifen kann, nur mit einer get-Funktion in der Klasse. Aber warum kann ich dann im Kopierkonstruktor darauf zugreifen?
Beispiel:
Field::Field(const Field& f)
{
pFirst = new T[f.capacity()];
pLast = pFirst + (f.pLast - f.pFirst);
pEnd = pFirst + (f.pEnd - f.pFirst);
std::copy(f.pFirst, f.pLast, pFirst);
}
Meine Erklärung:
private:
T *pFirst,*pLast,*pEnd;
c++
private
access-specifier
Dämonen König
quelle
quelle
const&
oder By-Value-Getter? Dann sind sie nur "Write-Private", & für Werte verschwenden Ressourcen und scheitern für nicht kopierbare Mitglieder.) Ich bin verblüfft über den Erfolg einer so leeren Frage, die nach der Erstellung von Kopien fragt und dabei völlig ignoriert, was dies bedeutet, und keine Antwort verwendet grundlegende Logik, um sie zu entlarven. Sie erklären trockene Techniken, aber es gibt eine viel einfachere Antwort auf eine Frage, die so blinzelteAntworten:
IMHO, vorhandene Antworten machen einen schlechten Job und erklären das "Warum" davon - konzentrieren sich zu sehr darauf, zu wiederholen, welches Verhalten gültig ist. "Zugriffsmodifikatoren funktionieren auf Klassenebene und nicht auf Objektebene." - Ja aber warum?
Das übergeordnete Konzept hier ist, dass es die Programmierer sind, die eine Klasse entwerfen, schreiben und pflegen, von denen erwartet wird, dass sie die gewünschte OO-Kapselung verstehen und befugt sind, ihre Implementierung zu koordinieren. Wenn Sie also schreiben
class X
, codieren Sie nicht nur, wie ein einzelnesX x
Objekt von Code mit Zugriff darauf verwendet werden kann, sondern auch wie:X
Objekte arbeiten zusammen , um beabsichtigte Verhaltensweisen bereitzustellen und gleichzeitig die Nachbedingungen und Invarianten Ihres Entwurfs zu berücksichtigen.Es ist nicht nur der Kopierkonstruktor - eine Vielzahl von Operationen kann zwei oder mehr Instanzen Ihrer Klasse umfassen: Wenn Sie vergleichen, addieren / multiplizieren / dividieren, kopieren, klonen, zuweisen usw., ist dies häufig der Fall Entweder muss es einfach Zugriff auf private und / oder geschützte Daten im anderen Objekt haben oder es soll eine einfachere, schnellere oder allgemein bessere Funktionsimplementierung ermöglichen.
Insbesondere möchten diese Vorgänge möglicherweise den privilegierten Zugriff nutzen, um Folgendes zu tun:
shared_ptr
s zum Referenzieren von Daten usw.auto_ptr<>
"verlagert" das Eigentum an dem im Bau befindlichen Objektunordered_map
Mitglied haben, aber nur öffentlich verfügbar machenbegin()
undend()
iterieren - mit direktem Zugriff aufsize()
Sie können Siereserve
schneller kopieren. Schlimmer noch, wenn sie nur aussetzenat()
undinsert()
und sonstthrow
....quelle
this == other
Sie bei jedem Zugriff darauf zugreifenother.x
müssen, wenn die Zugriffsmodifikatoren auf Objektebene funktionieren.this == other
jedes Mal , wenn du zugreifstother.x
" - verfehlt den Punkt - wennother.x
es nur zur Laufzeit akzeptiert wurde, wenn es äquivalent zu istthis.x
, würde es überhaupt nicht viel Zeigerschreiben gebenother.x
; Der Compiler könnte Sie genauso gut zwingen,if (this == other) ...this.x...
für alles zu schreiben, was Sie tun würden. Ihre Konzeption "Bequemlichkeit (noch mehr, wenn private Variablen öffentlich waren)" geht ebenfalls daneben - die Art und Weise, wie die Definition des Standards restriktiv genug ist, um eine ordnungsgemäße Kapselung zu ermöglichen , ist jedoch nicht unnötig unpraktisch.Die Zugriffsmodifikatoren arbeiten auf Klassenebene und nicht auf Objektebene .
Das heißt, zwei Objekte derselben Klasse können auf private Daten des jeweils anderen zugreifen.
Warum:
Vor allem aus Effizienzgründen. Es wäre ein nicht zu vernachlässigender Laufzeitaufwand, bei
this == other
jedem Zugriff zu überprüfen, obother.x
, ob die Zugriffsmodifikatoren auf Objektebene funktionieren würden.Es ist auch semantisch logisch, wenn Sie es in Bezug auf den Umfang betrachten: "Wie viel Teil des Codes muss ich beim Ändern einer privaten Variablen berücksichtigen?" - Sie müssen den Code der gesamten Klasse berücksichtigen, und dies ist orthogonal zu den Objekten, die zur Laufzeit vorhanden sind.
Und es ist unglaublich praktisch, wenn Sie Kopierkonstruktoren und Zuweisungsoperatoren schreiben.
quelle
Sie können innerhalb der Klasse auf private Mitglieder einer Klasse zugreifen, auch auf solche einer anderen Instanz.
quelle
Um die Antwort zu verstehen, möchte ich Sie an einige Konzepte erinnern.
this
Der Zeiger wird beim Aufruf an jede Funktion übergeben.Jetzt ist es wegen der
this
Zeigers, dass die Funktion in der Lage ist, Variablen dieser bestimmten Instanz zu lokalisieren. egal ob es privat oder öffentlich ist. Innerhalb dieser Funktion kann darauf zugegriffen werden. Wenn wir nun einen Zeiger auf ein anderes Objekt derselben Klasse übergeben. Mit diesem zweiten Zeiger können wir auf private Mitglieder zugreifen.Hoffe das beantwortet deine Frage.
quelle
Der Kopierkonstruktor ist eine Mitgliedsfunktion der Klasse und hat als solche Zugriff auf Datenelemente der Klasse, auch auf solche, die als "privat" deklariert sind.
quelle