std::unique_ptr и оператор '='
Может кто-нибудь объяснить разницу:
std::unique_ptr<int> item1(new int);
std::unique_ptr<int> item2 = item1;
Здесь вторая строчка вызывает ошибку, но если добавить функцию:
std::unique_ptr<int> createItem()
{
return std::make_unique<int>();
}
и вызвать
std::unique_ptr<int> item2 = createItem();
То все будет нормально. Но почему? Разве в двух случаях не вызывается один и тот же конструктор копирования?
Ответы (1 шт):
Для std::unique_ptr запрещено копирование. Разрешение только перемещение. При выполнении варианта с функцией и присваивание результата происходит перемещение возвращаемого результата функции в указатель. Поэтому код работает.
Чтобы работал и в первом случае можно добавить std::move, который приведёт аргумент к rvalue и позволит выполнить перемещение, а не копирование.
std::unique_ptr<int> item2 = std::move(item1);
В этом случае значение из item1 переходит в item2, т.е. item1 перестаёт владеть данными и становится пустым. Однако здесь вызывается не operator=, а происходит вызов перемещающего конструктора, т.к. объект item2 только создаётся. Если бы запись выглядела так:
item2 = std::move(item1);
При условии, что item2 создан где-то ранее, то тогда это уже было бы вызовом перемещающего operator=.