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

Почему в С++ нет выражения удаления места размещения?

Почему С++ не удаляет место размещения, которое напрямую соответствует новому месту размещения, т.е. вызывает деструктор и вызывает соответствующий оператор удаления места размещения?

Например:

MyType *p = new(arena) MyType;
...
//current technique
p->~MyType();
operator delete(p, arena);

//proposed technique
delete(arena) p;
4b9b3361

Ответ 1

operator delete уникален тем, что он не является членом или статической функцией-членом, которая динамически отправляется. Тип с виртуальным деструктором выполняет вызов собственного delete из самого производного деструктора.

struct abc {
    virtual ~abc() = 0;
};

struct d : abc {
    operator delete() { std::cout << "goodbye\n"; }
};

int main() {
    abc *p = new d;
    delete p;
}

(Запустите этот пример.)

Чтобы работать с удалением места размещения, деструктор должен каким-то образом передать дополнительные аргументы в operator delete.

  • Решение 1: Передайте аргументы через виртуальную функцию. Для этого требуется отдельный виртуальный деструктор для каждого статического члена и глобальной перегрузки operator delete с разными аргументами.
  • Решение 2:. Пусть виртуальный деструктор возвращает указатель функции вызывающему, указывающий, что нужно вызывать operator delete. Но если деструктор выполняет поиск, это касается той же проблемы, что требует определения нескольких виртуальных функций как # 1. Должен быть создан некоторый набор абстрактных перегрузок, который будет разрешать вызывающий.

У вас отличная возможность, и это было бы хорошим дополнением к языку. Вполне возможно, что дооснащение его существующей семантикой delete возможно даже теоретически. Но большую часть времени мы не используем полную функциональность delete, и достаточно использовать вызов псевдо-деструктора, за которым следует что-то вроде arena.release(p).

Ответ 2

Потому что нет необходимости, поскольку у нас уже есть ptr->~type();

Ответ 3

Возможно, потому, что существует синтаксис для явного вызова деструктора без освобождения (точно так же, как в вашем вопросе), но нет синтаксиса для явной конструкции в необработанной памяти?

Ответ 4

На самом деле существует удаление места размещения, которое вызывается реализацией для объекта, который был "выделен" с использованием размещения new, если конструктор создал исключение.

Из Википедии.

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

Ответ 5

Весь смысл размещения new - отделить создание объекта от управления памятью. Поэтому нет смысла связывать его во время уничтожения объекта.
Если память для ваших объектов находится в куче, и вы хотите, чтобы одно и то же время жизни для объектов и их памяти использовало только operator new и operator delete, возможно, переопределяя их, если вы хотите какого-либо особого поведения.
Размещение нового хорошо, например, в векторе, который хранит большой фрагмент необработанной памяти и создает и уничтожает объект внутри него, но не освобождает память.