C ++: продолжительность жизни временных аргументов? - PullRequest
60 голосов
/ 24 марта 2010

При создании нового экземпляра MyClass в качестве аргумента функции, например, так:

class MyClass
{
  MyClass(int a);
};    

myFunction(MyClass(42));

Стандарт дает какие-либо гранты на время деструктора?
В частности, могу ли я предположить, что он будет вызван до следующего оператора после вызова myFunction()?

Ответы [ 4 ]

98 голосов
/ 24 марта 2010

Временные объекты уничтожаются в конце полного выражения, частью которого они являются.

Полное выражение - это выражение, которое не является подвыражением какого-либо другого выражения. Обычно это означает, что он заканчивается на ; (или ) для if, while, switch и т. Д.), Обозначая конец оператора. В вашем примере это конец вызова функции.

Обратите внимание, что вы можете продлить срок службы временных файлов, связав их со ссылкой const. Это продлевает срок их службы до времени жизни ссылки:

MyClass getMyClass();

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

Если вы не планируете изменять возвращаемый объект, то это хороший способ сохранить вызов конструктора копирования (по сравнению с MyClass obj = getMyClass();), если оптимизация возвращаемого значения не применялась. К сожалению, это не очень хорошо известно. (Я предполагаю, что семантика перемещения в C ++ 11 сделает его менее полезным.)

23 голосов
/ 24 марта 2010

Каждый справедливо цитирует 12.2 / 3 или подобное, что отвечает на ваш вопрос:

Временные объекты уничтожаются как последний шаг в оценке полное выражение, которое (лексически) содержит точку, где они были создано.

Мне показалось забавным, что на следующей странице в моей печати стандарта 12.2 / 4 говорится:

Есть два контекста, в которых временные уничтожены на другая точка, чем конец полное выражение.

Ни один из них не относится к вашему примеру, они оба относятся к использованию временных значений в инициализаторах. Но это говорит о том, что вы должны сохранять смекалку, когда имеете дело с таким хитрым зверьком, как стандарт C ++.

10 голосов
/ 24 марта 2010

Стандарт действительно предлагает гарантии - из раздела 12.2 / 5:

Временная привязка к ссылке параметр в вызове функции (5.2.2) сохраняется до завершения полное выражение, содержащее вызов

Однако в вашем коде неясно, передается ли параметр по ссылке или по значению, хотя в какой-то момент будет использован конструктор копирования, который принимает ссылку.

3 голосов
/ 24 марта 2010

В разделе 12.2, Временные объекты, раздел 3, стандарт ANSI / ISO C гласит: «... Временные объекты уничтожаются в качестве последнего шага при оценке полного выражения, которое (лексически) содержит точку, в которой они были созданы . "

Это тесно связано с понятием Очки последовательности . Когда достигается точка последовательности, все побочные эффекты выражений гарантированно имеют место.

...