Classes and class hierarchies
C.81
Используйте `=delete` когда вы хотите отключить поведение по умолчанию (без желания предоставить альтернативу)
Причина
В нескольких случаях операция по умолчанию нежелательна.
Пример
class Immortal {
public:
~Immortal() = delete; // do not allow destruction
// ...
};
void use()
{
Immortal ugh; // error: ugh cannot be destroyed
Immortal* p = new Immortal{};
delete p; // error: cannot destroy *p
}
Пример
unique_ptr можно перемещать, но не копировать. Для этого его операции копирования удаляются. Чтобы избежать копирования, необходимо =delete его операции копирования из lvalue:
template<class T, class D = default_delete<T>> class unique_ptr {
public:
// ...
constexpr unique_ptr() noexcept;
explicit unique_ptr(pointer p) noexcept;
// ...
unique_ptr(unique_ptr&& u) noexcept; // move constructor
// ...
unique_ptr(const unique_ptr&) = delete; // disable copy from lvalue
// ...
};
unique_ptr<int> make(); // make "something" and return it by moving
void f()
{
unique_ptr<int> pi {};
auto pi2 {pi}; // error: no move constructor from lvalue
auto pi3 {make()}; // OK, move: the result of make() is an rvalue
}
Отметьте, что удалённые функции должны быть public.
Применение
Упразднение операции по умолчанию должно быть (и должно быть) основано на желаемой семантике класса. Рассматривайте такие классы с подозрением, но ведите «позитивный список» классов, где человек утверждал, что семантика корректна.