C ++: Lebensdauer temporärer Argumente?

Beim Erstellen einer neuen Instanz einer MyClass als Argument für eine function wie folgt:

 class MyClass { MyClass(int a); }; myFunction(MyClass(42)); 

Macht der Standard irgendeinen Empfänger zum Timing des Destruktors?
Kann ich konkret annehmen, dass es vor der nächsten statement nach dem Aufruf von myFunction() ?

Temporäre Objekte werden am Ende des vollständigen Ausdrucks zerstört, zu dem sie gehören.

Ein vollständiger Ausdruck ist ein Ausdruck, der kein Unterausdruck eines anderen Ausdrucks ist. Normalerweise bedeutet dies, dass es endet am ; (oder ) für if , while , switch usw.) das Ende der Aussage. In Ihrem Beispiel ist es das Ende des functionsaufrufs.

Beachten Sie, dass Sie die Lebensdauer von Provisorien verlängern können, indem Sie sie an eine const Referenz binden. Dies verlängert ihre Lebensdauer auf die Lebensdauer der Referenz:

 MyClass getMyClass(); { const MyClass& r = getMyClass(); // full expression ends here ... } // object returned by getMyClass() is destroyed here 

Wenn Sie nicht beabsichtigen, das zurückgegebene Objekt zu ändern, ist dies ein schöner Trick, um einen Aufruf eines Kopierkonstruktors zu speichern (im Vergleich zu MyClass obj = getMyClass(); ), falls die Rückgabewertoptimierung nicht angewendet wurde. Leider ist es nicht sehr bekannt. (Ich nehme an, dass C ++ 11s Bewegungssemantik es weniger nützlich macht.)

Jeder hat richtig 12,2 / 3 oder ähnliches zitiert, was deine Frage beantwortet:

Temporäre Objekte werden als letzter Schritt bei der Auswertung des vollständigen Ausdrucks gelöscht, der (lexikalisch) den Punkt enthält, an dem sie erstellt wurden.

Ich finde es amüsant, dass auf der nächsten Seite in meinem Druck des Standards, 12.2 / 4 sagt:

Es gibt zwei Kontexte, in denen Provisorien an einem anderen Punkt als dem Ende des Volltexts zerstört werden.

Keiner von ihnen gilt für Ihr Beispiel, beide beziehen sich auf die Verwendung von Provisorien in Initializern. Aber es zeigt, dass man bei einem trickreichen Biest wie dem C ++ – Standard mit dem Verstand umgehen muss.

Die Norm bietet tatsächlich Garantien – aus Abschnitt 12.2 / 5:

Eine temporäre Bindung an einen Referenzparameter in einem functionsaufruf (5.2.2) bleibt bestehen, bis der vollständige Ausdruck, der den Aufruf enthält, abgeschlossen ist

In Ihrem Code ist es jedoch nicht klar, ob der Parameter als Verweis oder als Wert übergeben wird, obwohl irgendwann ein Kopierkonstruktor verwendet wird, der eine Referenz übernimmt.

In Abschnitt 12.2, Temporäre Objekte, Klausel 3, der ANSI / ISO C-Standard besagt: “… Temporäre Objekte werden als der letzte Schritt bei der Bewertung der Voll-Ausdruck zerstört, die (lexikalisch) den Punkt enthält, wo sie erstellt wurden.”

Dies ist eng mit dem Konzept der Sequenzpunkte verbunden . Wenn ein Sequenzpunkt erreicht wird, sind garantiert alle Nebenwirkungen von Ausdrücken aufgetreten.