Копирование эмиссии происходит только тогда, когда копия не нужна. В частности, это когда есть один объект (назовите его A), который существует для продолжительности выполнения функции, и второй объект (вызовите его B), который будет копироваться из первого объекта, и сразу после этого , A будет уничтожен (т.е. при выходе из функции).
В этом конкретном случае стандарт дает разрешение для компилятора объединить A и B в два отдельных способа обращения к одному и тому же объекту.Вместо того, чтобы требовать, чтобы A было создано, B - копия, построенная из A, а затем A уничтожается, она позволяет рассматривать A и B как два способа обращения к одному и тому же объекту, поэтому (один) объект создается как A, и после того, как возврат функции начинает упоминаться как B, но даже если конструктор копирования имеет побочные эффекты, копия, которая создает B из A, может быть пропущена. Также обратите внимание, что в этом случае A (как объект, отдельный от B) никогда не уничтожается - например, если ваш dtor также имел побочные эффекты, они могли бы (быть) также опущены.
Ваш код не соответствует этому шаблону - первый объект не перестает существовать сразу же после его использования для инициализации второго объекта. После того, как F()
возвращает, есть два объекта экземпляра объекта. В этом случае Оптимизация возвращаемого значения [Именованная] (так называемая копия) просто не применяется.
Демо-код, когда будет применяться копия элизия:
#include <iostream>
struct foo {
foo(): a(5) { }
foo(const foo& f): a(f.a) { std::cout << "meep meep!\n"; }
int a;
};
int F() {
// RVO
std::cout << "F\n";
return foo();
}
int G() {
// NRVO
std::cout << "G\n";
foo x;
return x;
}
int main() {
foo a = F();
foo b = G();
return 0;
}
Оба MS VC++ и г ++ оптимизируют прочь и скопировать ctors из этого кода с включенной оптимизацией. g ++ оптимизирует оба варианта, даже если оптимизация отключена. Когда оптимизация отключена, VC++ оптимизирует анонимный доход, но использует копию ctor для именованного возврата.
Вы спрашиваете, почему вы создаете конструктор копирования, а не просто возвращаете значение поля исходного экземпляра? –
Откуда вы знаете, что это не было исключено. И почему вы думаете, что это должно было быть? Измените свой вопрос в отношении этих двух запросов. – 2010-04-26 22:33:41
@ Майкл, это правильно. –