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 :

Héritage privé et polymorphisme


Sujet :

Langage C++

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre éprouvé
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2007
    Messages
    142
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2007
    Messages : 142
    Par défaut Héritage privé et polymorphisme
    Bonjour,

    je suis tombé sur un test C++ avec la question suivante :
    Qu'affiche le code suivant :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    class A
    {
       public : virtual void f() {printf("A");}
    };
     
    class B : A
    {
       public : void f() {printf("B");}
    };
     
    A* a = new B();
    a->f();
    Et la réponse est... ne compile pas.

    En fait on ne peut pas faire car B hérite de A en privé.

    Mais j'aimerais comprendre pourquoi l'héritage privé interdit ceci puisque je pensais tout ce que faisait l'héritage privé, c'était de mettre tous les attributs et méthodes de A en privé dans B ?

    Merci de m'éclairer

  2. #2
    Futur Membre du Club
    Profil pro
    Inscrit en
    Août 2010
    Messages
    5
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2010
    Messages : 5
    Par défaut
    Peut-être tu aurais oublié public
    comme ceci

    class B : public A
    {
    public : void f() {printf("B");}
    };

  3. #3
    Rédacteur
    Avatar de 3DArchi
    Profil pro
    Inscrit en
    Juin 2008
    Messages
    7 634
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2008
    Messages : 7 634
    Par défaut
    Citation Envoyé par Lawyer666 Voir le message
    Mais j'aimerais comprendre pourquoi l'héritage privé interdit ceci puisque je pensais tout ce que faisait l'héritage privé, c'était de mettre tous les attributs et méthodes de A en privé dans B ?
    Ca permet de dissocier un héritage de type IS-A (publique) d'un héritage de type IS-IMPLEMENTED-IN-TERM-OF. Le premier est une relation très forte entre les classes parents et dérivées (cf LSP) alors que le second est 'un détail' d'implémentation et peut souvent être changé en composition. Cf F.A.Q. Quand dois-je faire un héritage public ? protégé ? privé ? et suivants.

  4. #4
    Membre éprouvé
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2007
    Messages
    142
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2007
    Messages : 142
    Par défaut
    arthurik >> Non justement, comme l'indique le titre du thread, c'est une question sur l'héritage privé !

    3DArchi >> Merci pour ces renseignements, mais je connais déjà tout ça en fait... je pose la question uniquement pour comprendre ce qui se passe. Pourquoi cette erreur de compil : "error C2243: 'type cast' : conversion from 'B *' to 'A *' exists, but is inaccessible"

    Flob90 >> Je t'avoue que je ne suis pas sur de comprendre ton explication... je vais y réfléchir et faire un petit test. Merci en tout cas.

    edit : OK, j'ai fait le test, le cast de B* en A* est effectivement accessible pour les méthodes de B, comme le dit Flob90.
    Et si j'ai bien compris, comme l'héritage est privé, on "ignore" dans le reste du code que B dérive de A, ce qui empêche ce cast !

  5. #5
    Membre Expert Avatar de Astraya
    Homme Profil pro
    Consommateur de café
    Inscrit en
    Mai 2007
    Messages
    1 048
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France

    Informations professionnelles :
    Activité : Consommateur de café
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Mai 2007
    Messages : 1 048
    Par défaut
    Un héritage privée consiste à dire en gros que seul l'enfant connait son parent, ni les petits enfants, ni le programme appelant ne peux savoir que B est un A. Seul B le sais! et il a accès au membre public et protected du parent uniquement.

    Pour un héritage public, tout le monde sait que B est le fils de A. Son fils n'a accès que aux méthodes public et protected

    Pour un héritage protected, c'est pareil que en privée. B a accès au membres public et protected de A mais il permet, contrairement à l'héritage privé, aux petits enfants de connaitre leur grand-parent A.

    Ici, l'héritage étant privée, tu ne peux instancier un B fils de A dans un A car personne ne sais que B est un A.

  6. #6
    Membre Expert

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Août 2004
    Messages
    1 391
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France, Doubs (Franche Comté)

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

    Informations forums :
    Inscription : Août 2004
    Messages : 1 391
    Par défaut
    Il ne l'a pas oublié, c'est une question d'un test ...

    Lorsque tu fais A* a = new B(); tu indique au compilateur de traiter le pointeur retourner par new comme un pointeur sur un A, alors que c'est un pointeur sur un B.

    Pour faire ceci le compilateur à besoin de pouvoir convertir le pointeur sur B en pointeur sur A, et pour ceci A doit être une base accessible de B, ce qui n'est pas le cas car l'héritage est privé et donc à part la classe personne ne sais que A est une base de B.

    Si tu fais ton cas dans une fonction membre de la classe B ca marche par contre.

    3DArchi t'a donné les raison OO (orienté objet, ie non spécifiquement lié au C++) de cette impossibilité, ce que je viens de te décrire et le mécanisme choisie par le C++ pour que ca fonctionne comme l'on s'y attend (héritage privé c'est implémenté-en-terme-de, et publique est-un). H. Sutter à écrit deux article sur l'héritage, ils sont très instructif.

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

Discussions similaires

  1. incompréhension héritage privé
    Par janyoura dans le forum Langage
    Réponses: 4
    Dernier message: 09/05/2012, 14h19
  2. héritage privé et virtuel
    Par Lawyer666 dans le forum C++
    Réponses: 7
    Dernier message: 24/07/2010, 01h34
  3. Héritage privé et opérateur de conversion
    Par Lavock dans le forum Langage
    Réponses: 7
    Dernier message: 21/06/2010, 19h25
  4. Template et héritage privé.
    Par 3DArchi dans le forum Langage
    Réponses: 6
    Dernier message: 18/09/2009, 09h36
  5. [héritage privé] appel du constructeur de base
    Par PINGOUIN_GEANT dans le forum C++
    Réponses: 4
    Dernier message: 19/10/2004, 14h05

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