Что я могу сделать с перемещенным объектом?


стандарт точно определяет, что я могу сделать с объектом после его перемещения? Раньше я думал, что все, что вы можете сделать с перемещенным объектом,-это уничтожить его, но этого было бы недостаточно.

например, возьмите шаблон функции swap Как определено в стандартной библиотеке:

template <typename T>
void swap(T& a, T& b)
{
    T c = std::move(a); // line 1
    a = std::move(b);   // line 2: assignment to moved-from object!
    b = std::move(c);   // line 3: assignment to moved-from object!
}

очевидно, что должно быть возможно назначить перемещенные объекты, иначе строки 2 и 3 не будут работать. Итак, что еще я могу сделать с перемещенными объектами? Где именно я могу найти эти данные в стандартный?

(кстати, почему это T c = std::move(a); вместо T c(std::move(a)); в строке 1?)

2 121

2 ответа:

перемещенные объекты существуют в неопределенном, но допустимом состоянии. Это говорит о том, что хотя объект, возможно, больше не способен делать многое, все его функции - члены должны по-прежнему демонстрировать определенное поведение-включая operator= - и все его члены в определенном состоянии-и он по-прежнему требует уничтожения. Стандарт не дает конкретных определений, потому что он будет уникальным для каждого UDT, но вы можете найти спецификации для стандартных типов. Некоторые, как контейнеры являются относительно очевидно - они просто перемещают свое содержимое, и пустой контейнер является четко определенным допустимым состоянием. Примитивы не изменяют перемещенный объект.

Примечание стороны: я считаю, что это T c = std::move(a) таким образом, если конструктор перемещения (или конструктор копирования, если перемещение не предусмотрено) является явным, функция завершится ошибкой.

17.6.5.15 [lib.типы.movedfrom]

объекты типов, определенных в стандартной библиотеке C++, могут быть перемещены из (12.8). Операции перемещения могут быть явно заданы или неявно сгенерированный. Если не указано иное, такие перемещаемые объекты должны быть помещен в допустимое, но неопределенное состояние.

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

примеры операций, которые вообще нет предпосылок:

  • уничтожение
  • задание
  • постоянные наблюдатели, такие как get,empty,size

примеры операций, которые вообще do есть предпосылки:

  • разыменования
  • pop_back

этот ответ теперь появляется в формате видео здесь:http://www.youtube.com/watch?v=vLinb2fgkHk&t=47m10s