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 :

Liste d'objets différents


Sujet :

C++

  1. #1
    Futur Membre du Club
    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    14
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Juillet 2006
    Messages : 14
    Points : 7
    Points
    7
    Par défaut Liste d'objets différents
    Bonjour à vous tous!

    Mon problème est le suivant. Je tente de créer une liste qui contient des objets différents. Cette liste contenant des objets différents, je me demande comment nouer les objets entre eux.

    Je commence par l'énumération des types possibles:

    // liste_objet.h

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    enum Type { CARRE , CERCLE };
    J'ai donc :

    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 liste{
     
    private:
     
    void * pdeb;
    void * pfin;
     
     
    public:
     
    //Fonctions permettant de gérer la liste
     
    void AjouteObjet(Type type);
     
    };
    Comme vous le voyez, les objets étant de nature différentes, je mes des void *.

    Maintenant, si je désire par exemple y nouer un objet carre, et un objet cercle, chacun étant issu d'une classe différente. (Je ne mes pas tout le code puisque je ne pense pas que cela soit nécessaire)

    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
     
    class carre{
     
    private : 
     
    void *psuiv;
    void *pprec;
     
    public:
     
    //Méthodes
     
    };
     
    class cercle{
     
    private:
     
    void *psuiv;
    void *pprec;
     
    public:
     
    //Méthodes
     
    };
    A ce moment, la définition des classes est faite. Je passe à l'implémentation des méthodes dans liste.cpp

    //liste_objet.cpp

    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
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    #include"liste_objet.h"
     
    void liste::AjouteObjet(Type type)
    {
     
    void *nouv;
     
    switch(type)
    {
        case CARRE:
     
        (carre*) nouv;
        nouv=new carre;
     
        if(!(this->pdeb)) {
        //Ici si il n'y a aucun élément dans la liste, il n'y a aucun problème,
        //je ne mes donc pas le code. 
       }
        //Par contre: 
        else{
     
            //Ici, si je décide d'ajouter un élément par la fin, j'aurai:
     
     
     
            //Il faut accéder au champ psuiv et pprec du dernier objet par             exemple(on ajoute par la fin). J'aurai besoin de ceci pour nouers les éléments:
     
            this->pfin->psuiv=nouv; //Ici est le problème
            nouv->pprec=this->pfin;
            nouv->psuiv=NULL;
            this->pfin=nouv;
        }
        break;
     
        case CERCLE:
            //Même problème
            break;
    }
     
    }
    Si je désire accéder à l'élément psuiv du dernier élément, le pointeur pfin étant un void à la base, il ne reconnait pas pfin comme pointant sur un objet carre ou cercle(logique). Ma question est donc la suivante, comment serait-il possible de mettre une liste comme celle-ci en place sans utiliser de void. Pour résoudre le problème des void * j'ai pensé créer une structure:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    typedef struct element{
        struct element * psuiv;
        struct element * pprec;
     
        void * objet;//Pointe vers un objet
        Type type;
    }element;
    Celle-ci permet de créer la même liste que ci-dessus, mais on plus de void * dans liste, mais bien des element * qui contiennent des .... void *. Comme element contient un type, je pense qu'il ne doit pas être difficile de caster le pointeur. On a donc une liste d'élement dont le contenu est un objet.

    Serait-il possible de faire cela autrement et plus facilement par exemple avec des patrons de fonctions et de classe ? J'espère être assez clair. Soyez indulgent, je sais bien que la clarté n'est pas mon fort, mais je fais comme je peux. Poser des questions si vous ne comprenez pas. Merci.

  2. #2
    Membre habitué Avatar de harsh
    Inscrit en
    Février 2005
    Messages
    229
    Détails du profil
    Informations forums :
    Inscription : Février 2005
    Messages : 229
    Points : 193
    Points
    193
    Par défaut
    D'un, , je lirais peut etre ensuite l'integralité de ta question...

    De deux, pour ton probleme, pas besoin d'utiliser le type void mais plutot l'heritage: tu construit un classe maillon dont derive tes classes maillonsCercle et maillonCarre par exemple
    Avant de poser une question, lire la Avant de répondre, lire la question

  3. #3
    Rédacteur

    Avatar de Matthieu Brucher
    Profil pro
    Développeur HPC
    Inscrit en
    Juillet 2005
    Messages
    9 810
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France, Pyrénées Atlantiques (Aquitaine)

    Informations professionnelles :
    Activité : Développeur HPC
    Secteur : Industrie

    Informations forums :
    Inscription : Juillet 2005
    Messages : 9 810
    Points : 20 970
    Points
    20 970
    Par défaut
    Ou mieux, tu fais dériver ta classe d'une classe parente Forme dans laquelle tu mets les méthodes - virtuelles - communes, puis tu utilises une liste ou tout autre conteneur de ces classes, à la place de reprogrammer une liste.

  4. #4
    Membre habitué Avatar de harsh
    Inscrit en
    Février 2005
    Messages
    229
    Détails du profil
    Informations forums :
    Inscription : Février 2005
    Messages : 229
    Points : 193
    Points
    193
    Par défaut
    Oui c'est sur, c'est bien mieux même.
    Avant de poser une question, lire la Avant de répondre, lire la question

  5. #5
    Futur Membre du Club
    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    14
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Juillet 2006
    Messages : 14
    Points : 7
    Points
    7
    Par défaut
    Dsl j'avais pas vu pour les balises. Merci de les avoir mises ! La prochaine fois je le ferai de suite .

    Merci pour les réponses. Je n'ai pas très bien compris pour les fonctions virtuelles . Par contre, si j'ai bien compris, en créant une liste, je doit faire comme ceci :

    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
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
     
     
    enum Type { CARRE, CERCLE };
     
    class maillon{
     
    private:
     
    maillon *psuiv;
    maillon *pprec;
     
    public:
     
    //méthodes sur les maillons
     
    }; 
     
     
    class forme{
     
    private:
     
    maillon *pdeb;
    maillon *pfin;
     
    public:
     
    //méthodes sur la liste forme
    void AjouteMaillon(Type);
     
    };
     
     
    class MaillonCercle : public maillon{
     
    ...
     
    };
     
    //idem avec MaillonCarre
    Par contre, pour ajouter un maillon de type MaillonCercle ou MaillonCarre:

    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
     
     
    void forme::AjouteMaillon(Type type)
    {
           switch(type)
           {
            case CERCLE:
     
            MaillonCercle *nouv;
            nouv=new MaillonCercle;
     
    //Est-ce que je peux déclarer ainsi MaillonCercle et le nouer avec le reste en le considérant comme un maillon normal,
    //même s'il y a déjà un MaillonCarre à la fin?
            nouv->pprec=this->pfin;
            this->pfin->psuiv=nouv;
            nouv->psuiv=NULL;
            this->pfin=nouv;
     
            break;
     
            case CARRE: //idem
            break;
    }
    Si j'ai fait une faute dites le moi parce que la fonction AjouteMaillon() me semble un peu bizarre quand même...

  6. #6
    Membre habitué Avatar de harsh
    Inscrit en
    Février 2005
    Messages
    229
    Détails du profil
    Informations forums :
    Inscription : Février 2005
    Messages : 229
    Points : 193
    Points
    193
    Par défaut
    Euuuhh... non, y a un petit melange la...

    Donc, tu créés une classe parent (bref une classe) Forme qui contient des fonction virtuelles (c'est a dire des fonctions qui ne seront définis que dans les classes filles... en TRES gros dans ton cas) comme isCarre() ou isCercle ou encore getType()... Ainsi, il ne te reste plus qu'a utiliser un conteneur tout fait de la std comme std::list pour faire une liste d'objet Forme.

    Pour l'heritage, tu dois je pense trouver ca dans la FAQ C++ mais ca donne un truc dans le genre:
    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
     
    class Forme
    {
    ...
    //ta déclaration de fonction virtuelles
    ...
    };
     
    class Cercle : public Forme
    {
    ...
    //la declaration des fonctions virtuelles que tu définis dans ton .cpp specifiquement pour Cercle
    ...
    };
     
    //idem pour toutes tes formes
    et ton main (ou autre)
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
     
    std::list< Forme > maList;
     
    //ajouter en debut
    maList.pushback( Cercle cer );
     
    //ajouter en fin
    maList.pushfront( Carre car );
    Avant de poser une question, lire la Avant de répondre, lire la question

  7. #7
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 519
    Points
    41 519
    Par défaut
    Euh... Tu crois que ça marche en sémantique de valeur ?

    Il me semble que pour ce genre de polymorphisme il faut utiliser une sémantique de référence (enfin, pour un conteneur STL, il faut utiliser des pointeurs)

    Code C++ : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    std::list< Forme * > maList;
     
    //ajouter en debut
    Cercle *pCercle = new Cercle(paramètres);
    maList.pushback( pCercle );
     
    //ajouter en fin
    Carre *pCarre = new Carre(autres paramètres);
    maList.pushfront( pCarre );
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  8. #8
    Rédacteur

    Avatar de Matthieu Brucher
    Profil pro
    Développeur HPC
    Inscrit en
    Juillet 2005
    Messages
    9 810
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France, Pyrénées Atlantiques (Aquitaine)

    Informations professionnelles :
    Activité : Développeur HPC
    Secteur : Industrie

    Informations forums :
    Inscription : Juillet 2005
    Messages : 9 810
    Points : 20 970
    Points
    20 970
    Par défaut
    Tout à fait, il faut passer par des pointeurs.

  9. #9
    Membre habitué Avatar de harsh
    Inscrit en
    Février 2005
    Messages
    229
    Détails du profil
    Informations forums :
    Inscription : Février 2005
    Messages : 229
    Points : 193
    Points
    193
    Par défaut
    Ca parait logique effectivement... mais qu'elles sont les règles exactes, ou plutot dans quel cas peut on utiliser un polymorphisme "de valeur" plutot que "de reference" ?
    Avant de poser une question, lire la Avant de répondre, lire la question

  10. #10
    Rédacteur

    Avatar de Matthieu Brucher
    Profil pro
    Développeur HPC
    Inscrit en
    Juillet 2005
    Messages
    9 810
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France, Pyrénées Atlantiques (Aquitaine)

    Informations professionnelles :
    Activité : Développeur HPC
    Secteur : Industrie

    Informations forums :
    Inscription : Juillet 2005
    Messages : 9 810
    Points : 20 970
    Points
    20 970
    Par défaut
    Un polymorphisme de référence, ça peut s'utiliser par exemple pour les streams - les surcharges des operator<< ou >> - par exemple, mais de manière général, c'est rare, car il faut manipuler de manière générale par valeur sauf dans certains cas.
    Dans 99% du temps, polymorphisme avec des pointeurs.

  11. #11
    Futur Membre du Club
    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    14
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Juillet 2006
    Messages : 14
    Points : 7
    Points
    7
    Par défaut
    Oki merci à vous je vais tenter comme ça et aller jeter un coup d'oeil à la FAQ. Je savais pas qu'il existait des conteneurs tout fait dans la STL . Voilà qui va déjà simplifier la tâche ^^ ... J'espère ne plus avoir de problèmes!

  12. #12
    Rédacteur

    Avatar de Matthieu Brucher
    Profil pro
    Développeur HPC
    Inscrit en
    Juillet 2005
    Messages
    9 810
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France, Pyrénées Atlantiques (Aquitaine)

    Informations professionnelles :
    Activité : Développeur HPC
    Secteur : Industrie

    Informations forums :
    Inscription : Juillet 2005
    Messages : 9 810
    Points : 20 970
    Points
    20 970
    Par défaut
    La STL, c'est justement presque que des conteneurs - à ne pas confondre avec la SL -

  13. #13
    Expert confirmé
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Décembre 2003
    Messages
    3 549
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Essonne (Île de France)

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

    Informations forums :
    Inscription : Décembre 2003
    Messages : 3 549
    Points : 4 625
    Points
    4 625
    Par défaut
    Il faut mieux utiliser boost::ptr_list<Forme> ou std::list<boost::clone_ptr<Forme> > pour mieux gérer la mémoire.
    Boost ftw

  14. #14
    Futur Membre du Club
    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    14
    Détails du profil
    Informations personnelles :
    Localisation : Belgique

    Informations forums :
    Inscription : Juillet 2006
    Messages : 14
    Points : 7
    Points
    7
    Par défaut
    Voilà, j'ai été jeté un coup d'oeil un peu partout pour trouver des info sur la STL (pas facile à trouver d'ailleurs, malgré la FAQ !). J'ai trouvé pas mal de chose, et je vais essayer de me débrouiller avec.

    J'ai créer une classe forme cette fois-ci contenant les méthodes virtuelles pures commune à toutes les formes. (Bouge(), Tourne(), Affiche(), Avance())

    J'ai définis les classes carre et cercle comme étant filles de formes. Dedand, j'y ai mis les méthodes virtuelles ainsi que leurs spécifications.

    Concernant l'arrangement de la liste, je dois donc créer cela à partir de la STL. Voilà, j'espère que ce coup-ci c'est bien ça qu'il faut faire lol. Merci !

  15. #15
    Expert éminent sénior
    Avatar de Luc Hermitte
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2003
    Messages
    5 275
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Août 2003
    Messages : 5 275
    Points : 10 985
    Points
    10 985
    Par défaut
    Citation Envoyé par Médinoc
    Euh... Tu crois que ça marche en sémantique de valeur ?
    C'est sûr que non. La sémantique de valeur est intrinsèquement incompatible avec les hiérarchies polymorphes.
    (Pour contourner, il faut feinter en passant par l'idiome enveloppe-lettre ou un truc dont j'ai oublié le nom et pour lequel il y a un article sur le site d'ASL d'Adobe (Je préférais Adam&Eve à ASL..))
    Blog|FAQ C++|FAQ fclc++|FAQ Comeau|FAQ C++lite|FAQ BS|Bons livres sur le C++
    Les MP ne sont pas une hotline. Je ne réponds à aucune question technique par le biais de ce média. Et de toutes façons, ma BAL sur dvpz est pleine...

  16. #16
    Expert confirmé
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Décembre 2003
    Messages
    3 549
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Essonne (Île de France)

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

    Informations forums :
    Inscription : Décembre 2003
    Messages : 3 549
    Points : 4 625
    Points
    4 625
    Par défaut
    (Pour contourner, il faut feinter en passant par l'idiome enveloppe-lettre ou un truc dont j'ai oublié le nom et pour lequel il y a un article sur le site d'ASL d'Adobe
    J'ai cherché vite fait j'ai pas trouvé, aurais-tu un lien ?
    Boost ftw

  17. #17
    Expert éminent sénior
    Avatar de Luc Hermitte
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2003
    Messages
    5 275
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Août 2003
    Messages : 5 275
    Points : 10 985
    Points
    10 985
    Par défaut
    Ce sont les regular objects
    http://opensource.adobe.com/wiki/ind...Regular_Object
    Visiblement il faut leur envoyer un mail en attendant qu'ils finissent de nétoyer leur wiki.
    Blog|FAQ C++|FAQ fclc++|FAQ Comeau|FAQ C++lite|FAQ BS|Bons livres sur le C++
    Les MP ne sont pas une hotline. Je ne réponds à aucune question technique par le biais de ce média. Et de toutes façons, ma BAL sur dvpz est pleine...

Discussions similaires

  1. Liste déroulante avec objet différent en VBA
    Par béber_novice dans le forum Général VBA
    Réponses: 1
    Dernier message: 16/04/2012, 20h07
  2. Tri d'une liste d'objet CObList
    Par cjacquel dans le forum MFC
    Réponses: 1
    Dernier message: 13/07/2005, 13h50
  3. [MFC] Retourner une liste d'objets
    Par 1cado dans le forum MFC
    Réponses: 10
    Dernier message: 28/07/2003, 12h11
  4. [Kylix] Composant - Liste d'objet
    Par Metal3d dans le forum EDI
    Réponses: 1
    Dernier message: 13/12/2002, 22h17
  5. liste d'objets
    Par Pierrot dans le forum Langage
    Réponses: 2
    Dernier message: 27/09/2002, 09h56

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