Es ist ein schmutziger Hack, aber man kann sie zerstören und rekonstruieren:
MyItemT&
MyItemT::operator=(const MyItemT& other)
{
if (this == &other) return *this; // "suggested" by Herb Sutter ;v)
this->MyItemT::~MyItemT();
try {
new(this) MyItemT(other);
} catch (...) {
new(this) MyItemT(); // nothrow
throw;
}
return *this;
}
Edit: damit ich meine Glaubwürdigkeit zu zerstören, ich weiß nicht wirklich, diese selbst tun, würde ich die const
entfernen. Ich habe jedoch darüber diskutiert, die Praxis zu ändern, denn const
ist einfach nützlich und besser zu verwenden, wo immer es möglich ist.
Manchmal wird zwischen der Ressource und dem von einem Objekt dargestellten Wert unterschieden. Ein Member kann durch Wertänderungen konstant sein, solange die Ressource gleich ist, und es wäre schön, die Kompilierungssicherheit dafür zu bekommen.
Bearbeiten 2: @Charles Bailey hat diesen wunderbaren (und sehr kritischen) Link zur Verfügung gestellt: http://gotw.ca/gotw/023.htm.
- Semantik ist in jeder abgeleiteten Klasse schwierig
operator=
.
- Es kann ineffizient sein, da es Zuweisungsoperatoren nicht aufruft, die definiert worden sind.
- Es mit wonky
operator&
Überlastungen unvereinbar ist (was auch immer)
- usw.
bearbeiten 3: die „welche Ressource“ vs „welchen Wert“ Unterscheidung Denken durch, so scheint es klar, dass operator=
sollte immer ändern der Wert und nicht die Ressource. Die Ressourcen-ID kann dann const
sein. In dem Beispiel sind alle Mitglieder const
. Wenn die "Info" ist, was in dem "Paket" gespeichert ist, dann sollte das Paket möglicherweise const
sein und die Information nicht.
Das Problem ist also nicht so sehr herauszufinden, die Semantik der Zuweisung als Mangel an einem offensichtlichen Wert in diesem Beispiel, wenn die "Info" tatsächlich Metadaten ist. Wenn die Klasse MyItemT
von einem Paket zu einem anderen wechseln will, muss sie entweder aufgeben und stattdessen auto_ptr<MyItemT>
verwenden oder zu einem ähnlichen Hack wie oben (der Identitätstest ist nicht erforderlich, aber catch
übrig) implementiert von außerhalb.Aber operator=
sollte nicht die Ressourcenbindung ändern, außer als eine besondere Funktion, die absolut nichts anderes stören wird.
Beachten Sie, dass diese Konvention gut zu Sutters Empfehlung passt, die Konstruktion von Kopien in Bezug auf die Zuweisung zu implementieren.
Wenn Ihre Klasse zuweisbar ist und diese Mitglieder geändert werden können, nehmen Sie die 'const' weg. Es macht einfach keinen Sinn. – GManNickG
@GMan - Ich denke du hast Recht. Ich suchte nach einem Freund-ähnlichen Ansatz, der es erlaubt, dass 'operator =' spezielle Privilegien hat, die verhindern, dass die Mitglieder manuell überschrieben werden. Aber nachdem ich gelesen habe, was @MichaelMozek gesagt hat, ist das überhaupt nicht sicher. – LeopardSkinPillBoxHat