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

C++ Discussion :

Héritage, type dynamique et méthode virtuelle


Sujet :

C++

  1. #1
    Membre éclairé Avatar de LinuxUser
    Inscrit en
    Avril 2007
    Messages
    857
    Détails du profil
    Informations forums :
    Inscription : Avril 2007
    Messages : 857
    Par défaut Héritage, type dynamique et méthode virtuelle
    Bonjour,

    J'ai un soucis avec l'héritage d'une méthode virtuelle.

    Supposons que l'on ait les classes suivantes:

    Classe Mere.h
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    class Mere
    {
      virtual void print() const;
      double m_membre1;
    }
    Classe Mere.cpp
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    void Mere::print() const
    {
      std::cout<<"\t"<<m_membre1;
    }
    Classe Fille.h
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    classe Fille : public Mere
    {
      virtual void print() const;
      double m_membre2;
    }
    Classe Fille.cpp
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
     
    void Fille::print() const
    {
      Mere::print();
      std::cout<<"\t"<<m_membre2;
    }
    Classe User.h
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    Classe User
    {
      void initialize(int age);
      Mere m_femme;
    }
    Classe User.cpp
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    void User::initialize(int age)
    {
      if(age>18)
      {
        m_femme = Mere();
      }
      else
      {
        m_femme = Fille();
      }
      m_femme.print(); // dans tous les cas appelle Mere::print() et donc n'affiche que m_membre1
    }
    Je ne comprends pas pourquoi lorrsque l'on construit une Fille, c'est quand même la méthode print() de la classe Mere qui est appelée.
    Et comment faire pour que Fille::print() soit appelée?

    Merci de votre aide.

  2. #2
    Membre très actif
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Janvier 2010
    Messages
    434
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Janvier 2010
    Messages : 434
    Par défaut
    C'est normal vu que tu manipule une classe mere.

    Le virtuel te permet de prioriser l'utilisation de la classe que tu manipule

    Va voir du coté des virtuel pure ou abstract pour avoir la réaction que tu recherche.

  3. #3
    Membre Expert
    Avatar de transgohan
    Homme Profil pro
    Développeur Temps réel Embarqué
    Inscrit en
    Janvier 2011
    Messages
    3 149
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Maine et Loire (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur Temps réel Embarqué

    Informations forums :
    Inscription : Janvier 2011
    Messages : 3 149
    Par défaut
    Un peu de lecture sur le polymorphisme sur la partie qui t'intéresse: http://cpp.developpez.com/faq/cpp/?p...isme_inclusion

  4. #4
    Membre éclairé Avatar de LinuxUser
    Inscrit en
    Avril 2007
    Messages
    857
    Détails du profil
    Informations forums :
    Inscription : Avril 2007
    Messages : 857
    Par défaut
    OK, j'y avais pensé, mais je fais de la Mere une classe abstraite et de Mere::print() une méthode virtuelle pure, elle ne sera pas implémentée, donc pas possible de factorisé dans la classe Fille.
    Je sais pas si j'ai été assez claire.
    Désolé si je dit des conneries, je viens du Java et j'ai un peu de mal avec le C++.

  5. #5
    Membre très actif
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Janvier 2010
    Messages
    434
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Janvier 2010
    Messages : 434
    Par défaut
    ton m_membre2 et m_membre1 sont initialisé dans le constructeur tu es sur qu'ils sont différent?

    Et fait le avec un pointeur de type Mere ça devrais passer.
    Le polymorphisme passe via un pointeur.

    Les virtuels pures c'est pour faire des interfaces donc pas nécessaire dans ton cas

  6. #6
    Membre éclairé Avatar de LinuxUser
    Inscrit en
    Avril 2007
    Messages
    857
    Détails du profil
    Informations forums :
    Inscription : Avril 2007
    Messages : 857
    Par défaut
    Oui ils sont initilisés dans leurs constructeurs respectifs (via list d'initialisation) et son différents, mais là n'est pas le problème, car le problème est que je déclare un membre de type Mere dans la classe User, er jen'arrive pas à l'utiliser comme une Fille, quoique je fasse ça reste une Mere.

    J'ai testé la manière indiquée dans la lien de transgohan, le problème est qu'en utilisant une méthode virtuelle pure, la classe Mere devient abstraite et je peux donc plus l'utiliser comme membre de la classe User (enfin je crois).

  7. #7
    Inactif  


    Homme Profil pro
    Inscrit en
    Novembre 2008
    Messages
    5 288
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Secteur : Santé

    Informations forums :
    Inscription : Novembre 2008
    Messages : 5 288
    Par défaut
    Salut

    A lire : différence entre le type static et le type dynamique dans la FAQ

    Comme le disait jouana, il faut passer par un pointeur (pour rappelle, en Java, tout est pointeur, donc polymorphique, en C++, il faut explicitement utiliser un pointeur) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    Classe User
    {
    public:
      ~User();
      void initialize(int age);
    private:
      Mere* m_femme;
    }
     
    // surtout ne pas oublier de delette !!!
    User::~User
    {
      if (m_femme)
        delete m_femme;
    }
     
    void User::initialize(int age)
    {
      if(age>18)
      {
        m_femme = new Mere();
      }
      else
      {
        m_femme = new Fille();
      }
      m_femme->print();
    }
    Ou encore mieux (dans ce code peut de risque niveau exception, mais autant prendre l'habitude d'utiliser les pointeurs intelligents) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    Classe User
    {
    public:
      // plus besoin de destructeur pour delette !
      void initialize(int age);
    private:
      std::unique_ptr<Mere> m_femme;
    }
     
    void User::initialize(int age)
    {
      if(age>18)
      {
        m_femme.reset(new Mere());
      }
      else
      {
        m_femme.reset(new Fille());
      }
      m_femme->print();
    }

  8. #8
    Membre éclairé Avatar de LinuxUser
    Inscrit en
    Avril 2007
    Messages
    857
    Détails du profil
    Informations forums :
    Inscription : Avril 2007
    Messages : 857
    Par défaut
    Super ça marche, du coup je dois travailler avec le pointeur à présent et plus avec la réference (notamment pour le getter()).
    Par contre, les pointeurs intellegents, est-ce quelque chose de portables, notemment sur système VMS/VAX (Alpha) ?

  9. #9
    Inactif  


    Homme Profil pro
    Inscrit en
    Novembre 2008
    Messages
    5 288
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Secteur : Santé

    Informations forums :
    Inscription : Novembre 2008
    Messages : 5 288
    Par défaut
    C'est dans le standard C++ (dans le nouvelle norme C++11), il suffit donc d'avoir un compilateur à jour. Sinon utiliser Boost. A priori, gcc est supporté sur Alpha

  10. #10
    Membre très actif
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Janvier 2010
    Messages
    434
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Janvier 2010
    Messages : 434
    Par défaut
    C'est un design pattern que tu peux mettre en place si tu le désire sinon mais si tu as une version qui l’intègre c'est mieux de l'utiliser

  11. #11
    Inactif  


    Homme Profil pro
    Inscrit en
    Novembre 2008
    Messages
    5 288
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Secteur : Santé

    Informations forums :
    Inscription : Novembre 2008
    Messages : 5 288
    Par défaut
    Citation Envoyé par jouana Voir le message
    C'est un design pattern que tu peux mettre en place si tu le désire sinon mais si tu as une version qui l’intègre c'est mieux de l'utiliser
    tu parles de quel design pattern ?

  12. #12
    Expert éminent

    Femme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2007
    Messages
    5 202
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 5 202
    Par défaut
    Citation Envoyé par LinuxUser Voir le message
    Super ça marche, du coup je dois travailler avec le pointeur à présent et plus avec la réference (notamment pour le getter()).
    Par contre, les pointeurs intellegents, est-ce quelque chose de portables, notemment sur système VMS/VAX (Alpha) ?
    en C++, tu as trois choses:
    la variable simple, la référence, et le pointeur.

    une variable simple contient une valeur de son propre type
    un pointeur contient une adresse vers de la mémoire qui sera interprétée conformément au type du pointeur.
    une référence est une variable qui donne son nom à une autre.

    Question typage, une variable simple à le même type statique que dynamique, tandis que les pointeurs et références autorise une différence entre les deux.
    Cependant, le type de la valeur désignée doit être compatible avec celui du désignant.

  13. #13
    Expert éminent
    Avatar de koala01
    Homme Profil pro
    aucun
    Inscrit en
    Octobre 2004
    Messages
    11 644
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 53
    Localisation : Belgique

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Octobre 2004
    Messages : 11 644
    Par défaut
    Salut,
    Citation Envoyé par jouana Voir le message
    C'est un design pattern que tu peux mettre en place si tu le désire sinon mais si tu as une version qui l’intègre c'est mieux de l'utiliser
    En fait, je présumes que tu voulais dire "c'est un concept"

    Un concept, c'est une idée générale qui peut etre mise en place dans n'importe quel langage (y compris les langages non orientés objets) basée sur des besoins simples, comme le concept de tableau, de pile, de file, de liste ou de boucle.

    Un desing pattern est ce que l'on appelle un "patron de conception" en français et correspond plus à la manière dont on va implémenter quelque chose, qui peut (ou non) être un concept.

    Ainsi, bien que je ne l'aime pas particulièrement, le patron de conception "singleton" est le moyen couramment utilisé pour implémenter le concept d'une instance systématiquement unique.

    Par contre, tu n'as aucun patron de conception pour représenter les concepts de boucle, de tableau, de pile ou de file

    Les pointeurs intelligents entrent donc dans la catégorie des concepts : ce sont des pointeurs qui sont en mesure de déterminer eux-même à quel moment il est le plus opportun d'être libérés, mais il n'y a pas de patron de conception qui nous indique comment le mettre en oeuvre (et pour cause : il y a plusieurs manières de le faire en fonction des circonstances )
    A méditer: La solution la plus simple est toujours la moins compliquée
    Ce qui se conçoit bien s'énonce clairement, et les mots pour le dire vous viennent aisément. Nicolas Boileau
    Compiler Gcc sous windows avec MinGW
    Coder efficacement en C++ : dans les bacs le 17 février 2014
    mon tout nouveau blog

  14. #14
    Inactif  


    Homme Profil pro
    Inscrit en
    Novembre 2008
    Messages
    5 288
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Secteur : Santé

    Informations forums :
    Inscription : Novembre 2008
    Messages : 5 288
    Par défaut
    Pour compléter (et parce que ça fait plus de 2 heures qu'on en a pas parlé), les pointeurs intelligents sont une mise en oeuvre du principe RAII

  15. #15
    Membre très actif
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Janvier 2010
    Messages
    434
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Janvier 2010
    Messages : 434
    Par défaut
    Je parlais des smartpointer je partais du principe que l'implémentation est un design pattern (patron de conception) qui à pour but d'éviter les problèmes récurant de fuite mémoire.

  16. #16
    Expert éminent
    Avatar de koala01
    Homme Profil pro
    aucun
    Inscrit en
    Octobre 2004
    Messages
    11 644
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 53
    Localisation : Belgique

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Octobre 2004
    Messages : 11 644
    Par défaut
    Citation Envoyé par jouana Voir le message
    Je parlais des smartpointer je partais du principe que l'implémentation est un design pattern (patron de conception) qui à pour but d'éviter les problèmes récurant de fuite mémoire.
    Smat pointers Vs pointeur intelligent, c'est blanc bonnet et bonnet blanc

    Mais non, un concept, c'est une chose qui va t'offrir certains services et fonctionnalités, alors qu'un patron de conception va t'indiquer les relations qui existent entre différents type pour justement te permettre d'implémenter les services et fonctionnalités que tu attends.

    Les patrons de conceptions sont apparus parce que, en observant correctement un grand nombre de projets d'envergure, on s'est rendu compte que des problèmes similaires amenaient à des solutions similaires, malgré le fait que tous les projets avaient leurs propres spécificités.

    Ils ne sont, en définitive, que l'expression de ce qu'on a pu observer, même s'ils sont maintenant considérés comme faisant partie des "bonnes pratiques" à respecter.

    Par contre, un concept, c'est une idée générale de ce que l'on attend d'un type particulier, indépendamment des relations qui peuvent lier ce type aux autres.

    C'est ainsi que le concept de pile est une collection d'objets gérés selon le principe LIFO, alors qu'une file est une collection d'objets gérés selon le principe FIFO.

    Pour les pointeur intelligents, il en va de même
    A méditer: La solution la plus simple est toujours la moins compliquée
    Ce qui se conçoit bien s'énonce clairement, et les mots pour le dire vous viennent aisément. Nicolas Boileau
    Compiler Gcc sous windows avec MinGW
    Coder efficacement en C++ : dans les bacs le 17 février 2014
    mon tout nouveau blog

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Héritage en diamant et méthodes virtuelles
    Par Neckara dans le forum C++
    Réponses: 9
    Dernier message: 06/10/2012, 17h15
  2. méthode virtuelle pure et héritage
    Par Invité dans le forum Langage
    Réponses: 3
    Dernier message: 20/07/2009, 22h12
  3. héritage et méthodes virtuelles ?
    Par Didine981 dans le forum C++
    Réponses: 4
    Dernier message: 08/12/2007, 13h43
  4. [Héritage] Downcasting et méthodes virtuelles
    Par poukill dans le forum C++
    Réponses: 8
    Dernier message: 16/07/2007, 13h38
  5. Exceptions, héritage et méthodes virtuelles
    Par Nuwanda dans le forum C++
    Réponses: 13
    Dernier message: 23/05/2006, 12h06

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