Probleme mit der Überladungsauflösung const / non-const

8

Ich habe eine Klasse, die ungefähr so ​​aussieht:

%Vor%

Außerhalb der Klasse rufe ich die Funktion Get () auf.

%Vor%

Ich erwarte, dass dies die öffentliche Version aufruft, aber stattdessen Visual Studio Fehler:

%Vor%

Wenn Sie die geschützte Überladung auskommentieren und alle Verweise darauf entfernen, wird der Code kompiliert.

Warum versucht der Compiler, das nicht zugreifbare Mitglied zu verwenden, wenn ein zugängliches Mitglied verfügbar ist? Gibt es eine akzeptierte Möglichkeit, den Compiler zu zwingen, die richtige Überladung zu wählen? Gibt es irgendwo einen Verweis auf die Auflösungsregeln für Mitgliedsfunktionen?

    
thekidder 04.06.2011, 21:52
quelle

2 Antworten

7

Es stimmt, dass die Überladungsauflösung vor den Zugänglichkeitsüberprüfungen stattfindet. Abschnitt 13.3 des Standards ( [over.match] ) sagt:

  

Die Überladungsauflösung ist ein Mechanismus zum Auswählen der besten aufzurufenden Funktion bei einer gegebenen Liste von Ausdrücken   die Argumente des Aufrufs und eine Menge von Kandidatenfunktionen, die basierend auf dem Kontext von aufgerufen werden können   der Anruf. Die Auswahlkriterien für die beste Funktion sind die Anzahl der Argumente, wie gut die Argumente sind   Übereinstimmung mit der Parametertypliste der Kandidatenfunktion, wie gut (für nicht statische Elementfunktionen)   Objekt entspricht dem impliziten Objektparameter und bestimmten anderen Eigenschaften der Kandidatenfunktion. [ Hinweis:   Die durch die Überladungsauflösung ausgewählte Funktion ist nicht garantiert für den Kontext geeignet. Andere   Einschränkungen, wie die Zugänglichkeit der Funktion, können ihre Verwendung in dem aufrufenden Kontext schlecht ausgebildet machen.   - Endnote]

Die übliche Lösung besteht darin, den öffentlichen und geschützten Funktionen unterschiedliche Namen zu geben.

Beachten Sie, das ist manchmal nützlich, Beispiel:

%Vor%

Beachten Sie, dass name_ref nur gelesen wird, daher ist es sinnvoll, const zu verwenden. % Co_de% referenzen können jedoch an Provisorien gebunden werden, und die Bindung von const an ein temporäres Objekt wäre eine dangling-Referenz, was zu undefiniertem Verhalten in name_ref führt.

%Vor%

Die private Konstruktorüberladung verhindert, dass eine temporäre do_something_with_name_ref() implizit erstellt und gebunden wird.

    
Ben Voigt 04.06.2011, 21:58
quelle
5

Die Überladungsauflösung wird zuerst durchgeführt und der Zugriff später überprüft.

Wenn Sie sowohl eine konstante als auch eine nicht-konstante Überladung haben, wird dies durch die Konstanz des Objekts, für das die Funktion aufgerufen wird, gelöst.

    
Bo Persson 04.06.2011 21:58
quelle