Pull to refresh

Что скрывает class Empty {}. Продолжение: с++ 11

Ранее, в 2009 году, была опубликована заметка о методах, которые С++ создаёт автоматически, даже если вы их не создавали.
Время течёт, все меняется, в том числе и язык с++. Давайте же посмотрим, что изменилось в области автоматически создаваемых методах с выходом 11 стандарта языка.

Теперь, если вы написали

class Empty {};


знайте, что на самом деле класс будет выглядеть следующим образом:

class Empty {
public:
  // Конструктор без параметров, как и ранее
  Empty();
  // Копирующий конструктор, как и ранее
  Empty(const Empty&);
  // Деструктор, как и ранее
  ~Empty();
  // Оператор присвоения, как и ранее
  Empty& operator=(const Empty&);
  // Оператор получения адреса, как и ранее
  Empty * operator&();
  // Оператор получения адреса константного объекта, как и ранее
  const Empty * operator&() const;
 // Перемещающий конструктор (нововведение)
  Empty(Empty&&);
 // Перемещающий оператор присваивания (нововведение)
 Empty& operator=(Empty&&);
};


Это не всё.

Генерация перемещающего конструктора и перемещающего оператора присваивания зависят друг от друга, от операций копирования и от деструктора.

Так, если Вы явно объявили операцию копирования, перемещающая операция сгенерирована не будет. И наоборот. При объявлении перемещающей операции не будет сгенерирована операция копирования.

Генерация операций копирования не зависят друг от друга и от деструктора, как и ранее.

С++ 11 даёт разработчику больше власти. Ранее, если какую либо из генерируемых операций необходимо было скрыть от пользовательского кода, её помечали как private без реализации. На самом деле, такой подход мог оставлять вопрос: не забыл ли программист просто напросто реализовать такую операцию? Даже если реализация была пустой, вопрос оставался:

скажем
.h
class Empty {
  private:
  Empty(const Empty&);
}

.cpp
  Empty::Empty(const Empty&){} // забыли реализовать?


В этом была некая неопределённость. Теперь же, С++ 11 позволяет явно указать что определённая операция нужна или не нужна. Для этого используются спецификаторы
=default
для генерации операции по умолчанию и
=delete

для отмены автоматической генерации

Предыдущий код в таком случае будет выглядеть так:
.h
class Empty {
  public:
  Empty(const Empty &) = delete;
}
Tags:
Hubs:
You can’t comment this publication because its author is not yet a full member of the community. You will be able to contact the author only after he or she has been invited by someone in the community. Until then, author’s username will be hidden by an alias.