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 :

[débutant] Question sur le polymorphisme


Sujet :

C++

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre Expert
    Avatar de coyotte507
    Profil pro
    Inscrit en
    Octobre 2006
    Messages
    1 327
    Détails du profil
    Informations personnelles :
    Âge : 35
    Localisation : France

    Informations forums :
    Inscription : Octobre 2006
    Messages : 1 327
    Par défaut [débutant] Question sur le polymorphisme
    Bonjour,

    je vais résumer mon problème. Est-ce que, lorsqu'on crée une classe dérivée dans un pointeur classe mère, on peut utiliser directements des élément présents seulement dans la classe dérivé via le pointeur?

    Par exemple, avec deux classe A et B:

    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
    class A()
    {
      public:
      A();
      ~A();
    };
     
    class B() : public A
    {
      public:
      B();
      ~B();
     
      int num;
    };
    le code suivant est-il valide:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    int main()
    {
      A *Pointeur;
      Pointeur = new B();
      Pointeur->num = 1;
      
      delete Pointeur;
      return 0;
    }
    Ma question se pose sur la ligne :
    Pointeur->num = 1;

    Si c'est valide, alors il y a un bug dans mon programme. Sinon, je vais devoir trouver une autre solution.

    Merci

  2. #2
    Expert confirmé
    Avatar de PRomu@ld
    Homme Profil pro
    Ingénieur de Recherche
    Inscrit en
    Avril 2005
    Messages
    4 155
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Vienne (Poitou Charente)

    Informations professionnelles :
    Activité : Ingénieur de Recherche
    Secteur : Enseignement

    Informations forums :
    Inscription : Avril 2005
    Messages : 4 155
    Par défaut
    e code suivant est-il valide:
    Non, tu ne peux pas faire ça. Déjà B n'hérite pas de A .

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    A = new B();
      A->num = 1;
     
      delete A;
    A est un type, ce que tu écris n'a pas de sens ...

  3. #3
    Membre Expert
    Avatar de coyotte507
    Profil pro
    Inscrit en
    Octobre 2006
    Messages
    1 327
    Détails du profil
    Informations personnelles :
    Âge : 35
    Localisation : France

    Informations forums :
    Inscription : Octobre 2006
    Messages : 1 327
    Par défaut
    voila j'ai édité (étourderies en masse comme tu as signalé)

    Je repose ma question ^^

  4. #4
    Expert confirmé
    Avatar de PRomu@ld
    Homme Profil pro
    Ingénieur de Recherche
    Inscrit en
    Avril 2005
    Messages
    4 155
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Vienne (Poitou Charente)

    Informations professionnelles :
    Activité : Ingénieur de Recherche
    Secteur : Enseignement

    Informations forums :
    Inscription : Avril 2005
    Messages : 4 155
    Par défaut
    En fait pour répondre à ta question, ça n'est pas possible et ne devrait pas compiler. En effet, pour le compilateur, le type (statique) est A or il n'y a pas de membre appelé num dans A.

    Si tu veux que ça fonctionne, il fait caster (dynmaic_cast) dans le type B.

  5. #5
    Membre Expert
    Avatar de coyotte507
    Profil pro
    Inscrit en
    Octobre 2006
    Messages
    1 327
    Détails du profil
    Informations personnelles :
    Âge : 35
    Localisation : France

    Informations forums :
    Inscription : Octobre 2006
    Messages : 1 327
    Par défaut
    d'accord merci

    je posai cette question car pour les fonctions virtuelles ca marchait.

  6. #6
    Expert confirmé
    Avatar de PRomu@ld
    Homme Profil pro
    Ingénieur de Recherche
    Inscrit en
    Avril 2005
    Messages
    4 155
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Vienne (Poitou Charente)

    Informations professionnelles :
    Activité : Ingénieur de Recherche
    Secteur : Enseignement

    Informations forums :
    Inscription : Avril 2005
    Messages : 4 155
    Par défaut
    Pour peu que la fonction déclarée virtuelle le soit dans la classe mère ça ne pose pas de problème.

  7. #7
    Membre averti
    Inscrit en
    Février 2007
    Messages
    14
    Détails du profil
    Informations forums :
    Inscription : Février 2007
    Messages : 14
    Par défaut
    Citation Envoyé par coyotte507
    ...
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    int main()
    {
      A *Pointeur;
      Pointeur = new B();
      Pointeur->num = 1;
      
      delete Pointeur;
      return 0;
    }
    Ma question se pose sur la ligne :
    Pointeur->num = 1;

    Si c'est valide, alors il y a un bug dans mon programme. Sinon, je vais devoir trouver une autre solution.

    Merci
    Si vous interessez à manipuler des champs dans votre classe autres que les fonctions;
    par ex:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    Pointeur->num = 1;
    vous pouvez utilisez des fonctions telles que les Getters et les Setters
    par ex :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    virtual setNum(int param){num = param}; // num recoit param
    ....
    MaClasseMere.setNum(1);
    Le polymorphisme du C++ est un polymorphisme par sous-typage , et il est possible pour les fonctions virtuelles , les classes virtuelles et je ne sais pas s'il y a d'autres déclarations virtuelles possibles mais ca serai inutile de faire :
    or les fonctions faitent toutes les manipulations possibles sur les champs d'une classe.

  8. #8
    Expert confirmé
    Avatar de PRomu@ld
    Homme Profil pro
    Ingénieur de Recherche
    Inscrit en
    Avril 2005
    Messages
    4 155
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Vienne (Poitou Charente)

    Informations professionnelles :
    Activité : Ingénieur de Recherche
    Secteur : Enseignement

    Informations forums :
    Inscription : Avril 2005
    Messages : 4 155
    Par défaut
    Citation Envoyé par rebassou
    Si vous interessez à manipuler des champs dans votre classe autres que les fonctions;
    par ex:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    Pointeur->num = 1;
    vous pouvez utilisez des fonctions telles que les Getters et les Setters
    par ex :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    virtual setNum(int param){num = param}; // num recoit param
    ....
    MaClasseMere.setNum(1);
    Ca c'est un problème d'encapsulation et pas de polymorphisme.

    Le polymorphisme du C++ est un polymorphisme par sous-typage , et il est possible pour les fonctions virtuelles , les classes virtuelles et je ne sais pas s'il y a d'autres déclarations virtuelles possibles mais ca serai inutile de faire :
    or les fonctions faitent toutes les manipulations possibles sur les champs d'une classe.
    Il en va quasiment de même pour tous les langages polymorphiques. Mais je ne suis pas convaincu que tout le polymorphisme soit du sous-typage (j'imagine qu'il y a des particularités du sous-typage qui ne relèvent pas du sous-typage).

  9. #9
    Rédacteur
    Avatar de Laurent Gomila
    Profil pro
    Développeur informatique
    Inscrit en
    Avril 2003
    Messages
    10 651
    Détails du profil
    Informations personnelles :
    Âge : 41
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Avril 2003
    Messages : 10 651
    Par défaut
    Ici ce serait plutôt un problème de conception : si tu veux manipuler les données particulières d'un B, alors il te faut un B*. Si tu stockes des A* c'est que les traitements que tu leur fait subir sont cohérents avec l'interface de A, et que tu n'as pas besoin de savoir le type dynamique des instances.

    Le polymorphisme du C++ est un polymorphisme par sous-typage
    Pas uniquement. Le polymorphisme statique (via templates) n'a rien à voir avec le sous-typage.

  10. #10
    Expert confirmé

    Inscrit en
    Novembre 2005
    Messages
    5 145
    Détails du profil
    Informations forums :
    Inscription : Novembre 2005
    Messages : 5 145
    Par défaut
    Citation Envoyé par Laurent Gomila
    Pas uniquement. Le polymorphisme statique (via templates) n'a rien à voir avec le sous-typage.
    L'aspect statique/dynamique du polymorphisme est quasiment indépendant de la classification coercion, surcharge, substitution, paramétrique.

    Les 8 combinaisons existent (mais pas toutes en C++, il y manque de la coercion et du polymorphisme paramètrique dynamique; le polymorphisme de substitution statique est présent avec 0 qui est un pointeur nul pour tout les types pointeurs).

    Les templates fournissent aussi de la surcharge (avec les spécialisations explicites)

  11. #11
    Expert confirmé

    Inscrit en
    Novembre 2005
    Messages
    5 145
    Détails du profil
    Informations forums :
    Inscription : Novembre 2005
    Messages : 5 145
    Par défaut
    Citation Envoyé par PRomu@ld
    Mais je ne suis pas convaincu que tout le polymorphisme soit du sous-typage (j'imagine qu'il y a des particularités du sous-typage qui ne relèvent pas du sous-typage).
    Je ne comprends pas ce que tu veux dire.

  12. #12
    Membre averti
    Inscrit en
    Février 2007
    Messages
    14
    Détails du profil
    Informations forums :
    Inscription : Février 2007
    Messages : 14
    Par défaut
    Citation Envoyé par PRomu@ld
    Ca c'est un problème d'encapsulation et pas de polymorphisme.
    D'abord vous ditez ce n'est pas un problème de polymorphisme et vous proposez le dynmaic_cast qui demande la presence d'une classe de base polymorphique. Il est fonctionnel pour les classes visibles(ici probleme d'encapsulation dans le type d'heritage ).
    Or l'encapsulation est evidante est tjrs présente, alors si on ne souhaite pas utiliser le transtypage dynamique de meme on rende la classe générique avec la notion de polymorphisme.

    Mais je ne suis pas convaincu que tout le polymorphisme soit du sous-typage (j'imagine qu'il y a des particularités du sous-typage qui ne relèvent pas du sous-typage).
    vous avez raison de le dire, je n'ai pas rencontré tous les sous-typages !!

    Citation Envoyé par coyotte507
    Par exemple, avec deux classe A et B:

    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
    class A()
    {
      public:
      A();
      ~A();
    };
     
    class B() : public A
    {
      public:
      B();
      ~B();
     
      int num;
    };
    le code suivant est-il valide:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    int main()
    {
      A *Pointeur;
      Pointeur = new B();
      Pointeur->num = 1;
      
      delete Pointeur;
      return 0;
    }
    Oui c possible avec le sous-typage par pointeur.
    Attention :
    ->Dans ce qui suit les conversions existantes sont légales et implicites.
    ->Les compilateurs ne sont pas les meme, c'est possible qu'une compilation correcte dans un compilateur soit fausse dans un autre.
    ->Cette exemple ne repond pas au probleme d'encapsulation et du polymorphisme, il s'agit d'une situation simple.
    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
     
    //Compilateur Borland C++ Ver 5.02
    #include <iostream.h>
     
    class A{ public:void f();};
    class B: public A{
    	public:
       	void g();
            int num;
    };
    void A::f(){cout << "Calsse A" << endl;}
    void B::g(){cout << "Calsse B" << endl;}
     
    void main(){
    	A *aa;
    	B *bb;
    	bb = new B();
    	aa = bb;
    	aa->f();
    	bb->f();
            bb->num = 1;
            cout << bb->num;
            //mn compilateur quite à la fin de l'application  pour faire une pause 
            char ch;
            cin >> ch;
    }

  13. #13
    Membre Expert
    Avatar de coyotte507
    Profil pro
    Inscrit en
    Octobre 2006
    Messages
    1 327
    Détails du profil
    Informations personnelles :
    Âge : 35
    Localisation : France

    Informations forums :
    Inscription : Octobre 2006
    Messages : 1 327
    Par défaut
    Merci pour vos réponses

    rebassou merci de m'avoir montré cette astuce, je vais l'utiliser.

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

Discussions similaires

  1. [Héritage] Question sur le polymorphisme
    Par nikhil dans le forum C++
    Réponses: 7
    Dernier message: 28/12/2005, 20h33
  2. [débutant] Questions sur le Transact-SQL
    Par nagty dans le forum MS SQL Server
    Réponses: 7
    Dernier message: 05/07/2005, 17h43
  3. [parseur] [Débutant] Question sur les parseurs
    Par steph-n dans le forum XML/XSL et SOAP
    Réponses: 5
    Dernier message: 02/05/2005, 19h17
  4. [Débutant] questions sur Visibroker
    Par Man Dak dans le forum CORBA
    Réponses: 1
    Dernier message: 29/06/2004, 23h02
  5. [débutant] question sur les #
    Par Ultros dans le forum C
    Réponses: 3
    Dernier message: 29/04/2004, 12h30

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