Ответ
В C++ деструкторы вызываются в строго определённом порядке, обратном порядку конструирования:
- Для одного объекта: Тело деструктора самого класса выполняется первым.
- Для членов класса (полей): Деструкторы полей вызываются после тела деструктора класса, в порядке, обратном их объявлению в определении класса.
- Для базовых классов: Деструкторы базовых классов вызываются после деструкторов всех полей, в порядке, обратном порядку наследования.
- Для объектов в стеке: При выходе из области видимости деструкторы локальных объектов вызываются в порядке LIFO (последний созданный — первый уничтоженный).
Пример, демонстрирующий порядок:
#include <iostream>
#include <string>
class Member1 {
public:
~Member1() { std::cout << "Member1 destroyed.n"; }
};
class Member2 {
public:
~Member2() { std::cout << "Member2 destroyed.n"; }
};
class Base {
public:
~Base() { std::cout << "Base destroyed.n"; }
};
class Derived : public Base {
Member1 m1; // Объявлен первым
Member2 m2; // Объявлен вторым
public:
~Derived() {
std::cout << "Derived body.n"; // Тело деструктора
}
};
int main() {
Derived d;
// При выходе из main() для объекта 'd' порядок будет:
// 1. Тело ~Derived()
// 2. ~Member2() (обратный порядок объявления полей)
// 3. ~Member1()
// 4. ~Base() (обратный порядок наследования)
return 0;
}
Ожидаемый вывод:
Derived body.
Member2 destroyed.
Member1 destroyed.
Base destroyed.