C ++ стек выделенный объект, явный вызов деструктора - PullRequest
6 голосов
/ 28 октября 2009

Я столкнулся со странным использованием деструктора во время работы над существующей библиотекой. Деструктор стека, выделенного вектора stl, вызывался явно, когда дело в том, что этот объект, возможно, придется использовать снова. Эти векторные объекты являются слегка настраиваемой версией векторного класса stl, имеющего специализированный метод clear. В теле деструктора существуют два вызова метода: clear(), _Tidy().

Я пытался придумать вескую причину, почему этот деструктор вызывается, а не просто clear, но я в растерянности. Кто-нибудь пролил свет на то, почему это может быть хорошей идеей?

Ответы [ 5 ]

9 голосов
/ 28 октября 2009

clear () не гарантирует фактического освобождения выделенной памяти в векторе; _Tidy () в реализации MSVC фактически освободит это хранилище, так что это, вероятно, было сделано как оптимизация.

Это зло, но вы можете сделать это легально (без неопределенного поведения), если хранилище повторно используется объектом того же типа (без учета cv-квалификаторов), который занимает ровно все хранилище:

T automatic;
automatic.T::~T();
new (&automatic) T();

Раздел 3.8.7 стандарта C ++ описывает этот сценарий использования и объясняет его законность; он даже включает пример, аналогичный приведенному выше.

5 голосов
/ 28 октября 2009

Большой вектор?

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

std::vector<T>().swap(vector_to_clear);

для очистки вектора для повторного использования и очистки выделенной памяти.

Возможно, оригинальный автор не знал шаблона и пытался избавиться от выделенной памяти таким злым способом. (Думаю _Tidy освобождает выделенную память)

5 голосов
/ 28 октября 2009

Может ли этот класс использовать какой-то метод размещения ? Это единственный раз, когда я вижу явные деструкторы в использовании.

1 голос
/ 28 октября 2009

Может быть, оригинальный кодер позаботился о том, где в памяти были размещены объекты.

Тогда деструктор должен вызываться явно, согласно этому обсуждению .

1 голос
/ 28 октября 2009

Это определенно не очень хорошая идея. Любая операция над объектом после запуска деструктора приводит к неопределенному поведению.

...