Sobes.tech
Junior — Middle

Quelles sont les conséquences possibles lors de l'appel d'une fonction virtuelle dans le destructeur d'un objet?

sobes.tech IA

Réponse de l'IA

Lorsqu'une fonction virtuelle est appelée à l'intérieur du destructeur d'un objet en C++, c'est la version de la fonction correspondant au type actuel de l'objet lors de la destruction qui est appelée, et non celle de la classe dérivée. Cela est dû au fait qu'au moment de l'exécution du destructeur, l'objet a déjà été "réduit" à la classe de base, et le mécanisme d'appels virtuels ne prend pas en compte les classes dérivées.

Conséquences :

  • Si la fonction virtuelle a été redéfinie dans la classe dérivée, l'appel dans le destructeur de la classe de base n'invoquera pas cette version redéfinie, mais la version de la classe de base.
  • Cela peut entraîner un comportement inattendu ou des erreurs si la fonction dépend de l'état de la classe dérivée, qui a déjà été détruit.

Exemple :

#include <iostream>

struct Base {
    virtual ~Base() {
        foo(); // appel à une fonction virtuelle
    }
    virtual void foo() { std::cout << "Base::foo" << std::endl; }
};

struct Derived : Base {
    ~Derived() override {
        std::cout << "Destructeur de Derived" << std::endl;
    }
    void foo() override { std::cout << "Derived::foo" << std::endl; }
};

int main() {
    Base* obj = new Derived();
    delete obj; // appellera Base::~Base(), dans lequel foo() appellera Base::foo
}

La sortie sera :

Destructeur de Derived
Base::foo

Ainsi, l'appel d'une fonction virtuelle dans le destructeur n'appelle pas la version redéfinie de la classe dérivée.