Подтвердить что ты не робот

Почему мне разрешено копировать unique_ptr?

Возможный дубликат:
Возврат unique_ptr из функций

20.7.1.2 [unique.ptr.single] определяет конструктор копирования следующим образом:

// disable copy from lvalue
unique_ptr(const unique_ptr&) = delete;
unique_ptr& operator=(const unique_ptr&) = delete;

Итак, почему компилируется следующий код?

#include <memory>
#include <iostream>

std::unique_ptr< int > bar()
{
  std::unique_ptr< int > p( new int(4));
  return p;
}

int main()
{
  auto p = bar();

  std::cout<<*p<<std::endl;
}

Я скомпилировал его следующим образом:

g++ -O3  -Wall -Wextra -pedantic -std=c++0x kel.cpp

Компилятор: g++ version 4.6.1 20110908 (Red Hat 4.6.1-9)

4b9b3361

Ответ 1

В операторе return, если вы возвращаете локальную переменную, выражение рассматривается как rvalue и, таким образом, автоматически перемещается. Это похоже на:

  return std::move(p);

Он вызывает конструктор unique_ptr(unique_ptr&&).

В основной функции bar() создает временную, которая является rvalue, и также правильно перемещается в p в main.

Ответ 2

Скопирован не, он перемещается.

Оператор return эквивалентен этому:

return std::move(p);

Педантично, это семантически эквивалентно. На самом деле компилятор может оптимизировать код, возвращая вызов вызову-конструктору. Но это возможно, только если вы напишете его как:

return p; //It gives the compiler an opportunity to optimize this. 

Это рекомендуется. Однако компилятор не имеет возможности оптимизировать, если вы пишете это:

return std::move(p); //No (or less) opportunity to optimize this. 

Это не.: -)

Ответ 3

Я думаю, что копирование из lvalue отключено, но "bar()" является rvalue, поэтому он в порядке. Вы определенно должны иметь возможность копировать из rvalues.