IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Langage C++ Discussion :

Heritage non virtuel.


Sujet :

Langage C++

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2009
    Messages
    69
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2009
    Messages : 69
    Par défaut Heritage non virtuel.
    Bonjour,

    Je vois dans les exemples de la libraire boost.ggl des trucs comme :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    struct my_ring : std::deque<my_point> {};
    Je pensais qu'il y avait des risques ? par exemple si on a dans le code un :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    std::deque<my_point> * truc;
    //...
     truc  = new my_ring();
    //...
    delete truc;
    truc = nullptr;
    Alors il y a bien une fuite mémoire, non?

    Bref, tout ceci signifie-t-il que "tant qu'on essaie pas de faire du polymorphisme, on ne risque rien à faire des destructeur non virtuels" ?

    ElPedro.

  2. #2
    Membre expérimenté Avatar de vikki
    Profil pro
    Inscrit en
    Mai 2007
    Messages
    292
    Détails du profil
    Informations personnelles :
    Âge : 40
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations forums :
    Inscription : Mai 2007
    Messages : 292
    Par défaut
    Bonjour,

    Je vois dans les exemples de la libraire boost.ggl des trucs comme :
    Code :


    struct my_ring : std::deque<my_point> {};


    Je pensais qu'il y avait des risques ? par exemple si on a dans le code un :
    Code :


    std::deque<my_point> * truc;
    //...
    truc = new my_ring();
    //...
    delete truc;
    truc = nullptr;


    Alors il y a bien une fuite mémoire, non?

    Bref, tout ceci signifie-t-il que "tant qu'on essaie pas de faire du polymorphisme, on ne risque rien à faire des destructeur non virtuels" ?
    Hello,
    Le destructeur de my_ring ne devrait effectivement pas être appelé dans ce cas (le destructeur de deque (ou de ses classes mères) n'est pas virtuel). Mais si l'on se contente d'ajouter des fonctionnalités dans my_ring et pas de nouveaux membres, cela n'a pas d'importance (je crois).
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    struct my_ring : std::deque<my_point> {};
    C'est vraiment ca que tu as vu? Dans ce cas, un simple typedef me semble équivalent.

  3. #3
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2009
    Messages
    69
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2009
    Messages : 69
    Par défaut
    >>>Dans ce cas, un simple typedef me semble équivalent.
    1/ la remarque est interessante 2/ cependant je ne suis pas du tout d'accord :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    typedef std::string IdVoiture;
    typedef std::string IdAvion;
     
    void destroy(IdVoiture v);
    void destroy(IdAvion v);
    //==> PROBLEME : ambiguite
    tandis qu'avec l'héritage il n'y a aucun soucis!
    (C'est d'ailleurs l'une des raisons initiales de ce post (copie de type)).

    Par ailleurs, il n'y a pas de raison pour laquelle la classe heritee fasse la meme taille que la classe initiale (même si les compilos actuels font attention à cela souvent). Ceci implique donc une fuite mémoire de toute façon si on fait un "delete classeBase".

    Bref je réitère ma question :
    tout ceci signifie-t-il que "tant qu'on essaie pas de faire du polymorphisme, on ne risque rien à faire des destructeur non virtuels" ?

  4. #4
    Membre expérimenté Avatar de vikki
    Profil pro
    Inscrit en
    Mai 2007
    Messages
    292
    Détails du profil
    Informations personnelles :
    Âge : 40
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations forums :
    Inscription : Mai 2007
    Messages : 292
    Par défaut
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    typedef std::string IdVoiture;
    typedef std::string IdAvion;
     
    void destroy(IdVoiture v);
    void destroy(IdAvion v);
    //==> PROBLEME : ambiguite
    Effectivement, le typedef ne permet pas la surcharge de fonction. Mais comme il ne s'agit pas d'un héritage à but polymorphique, l'intérêt est moindre (même si ca peut servir c'est vrai).

    Par ailleurs, il n'y a pas de raison pour laquelle la classe heritee fasse la meme taille que la classe initiale (même si les compilos actuels font attention à cela souvent). Ceci implique donc une fuite mémoire de toute façon si on fait un "delete classeBase".
    Il me semble au contraire que dans ce cas, un objet de la classe fille fera la même taille qu'un objet de la classe mère (un sizeof le confirme).

  5. #5
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2009
    Messages
    69
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2009
    Messages : 69
    Par défaut
    le sizeof c'est celui de ton compilo .
    bref, sur Wii, PS3 ou AS400 il n y'a aucune raison pour que tu obtiennes le même résultat. Même entre visual 6 et visual 9 tu as des différences à ce niveau là.

    L'utilite de l'heritage est :
    1/ pour faire écrire des templates
    2/ levee d'ambiguitée. Par exemple, dans le cas de string si tu manipule des IdVoiture incompatibles avec des IdAvions tu ne risques pas de les confondre : le compilateur te le dira. Et plus tard tu peux même changer le type pour une version plus complète sans difficultés.

    Cependant je me pose la question : est-ce sans risque?

  6. #6
    Membre expérimenté Avatar de vikki
    Profil pro
    Inscrit en
    Mai 2007
    Messages
    292
    Détails du profil
    Informations personnelles :
    Âge : 40
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations forums :
    Inscription : Mai 2007
    Messages : 292
    Par défaut
    le sizeof c'est celui de ton compilo .
    bref, sur Wii, PS3 ou AS400 il n y'a aucune raison pour que tu obtiennes le même résultat. Même entre visual 6 et visual 9 tu as des différences à ce niveau là.
    Je ne te suis pas. Tu compile ton code avec 1 compilateur à la fois (en tout cas ca me parait logique), et un sizeof(ma_structure) renverra la même valeur dans tout ton programme. Si tu hérite d'une classe sans ajouter de nouveaux membre on devrait avoir (me semble) sizeof(mère)==sizeof(fille), quelque soit le compilateur.

    L'utilite de l'heritage est :
    1/ pour faire écrire des templates
    2/ levee d'ambiguitée. Par exemple, dans le cas de string si tu manipule des IdVoiture incompatibles avec des IdAvions tu ne risques pas de les confondre : le compilateur te le dira. Et plus tard tu peux même changer le type pour une version plus complète sans difficultés.
    Là je te suis plus du tout

Discussions similaires

  1. Double héritage (virtuel et non virtuel)
    Par oodini dans le forum Langage
    Réponses: 9
    Dernier message: 09/11/2012, 14h15
  2. Heritage, Fonction virtuelle et cast
    Par NoIdea dans le forum C++
    Réponses: 13
    Dernier message: 11/04/2010, 12h24
  3. heritage multiple virtuel et warning 4250
    Par babar63 dans le forum C++
    Réponses: 3
    Dernier message: 10/03/2009, 18h49
  4. Creation Hyperlink sur un dossier non virtuel du serveur
    Par predalpha dans le forum ASP.NET
    Réponses: 2
    Dernier message: 13/05/2008, 15h55
  5. Réponses: 7
    Dernier message: 20/12/2007, 15h13

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo