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 :

Problème de destructeur avec Dev C++


Sujet :

C++

  1. #1
    Membre habitué
    Profil pro
    Inscrit en
    Avril 2008
    Messages
    10
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2008
    Messages : 10
    Par défaut Problème de destructeur avec Dev C++
    Bonjour,

    Je vais d'abord vous mettre le code où est le problème. Le programme gère des parties et des joueurs d'échecs.

    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
    #include <cstdlib>
    #include <iostream>
    #include "Joueur.h"
    #include "partie.h"
    using namespace std;
     
    int main(void)
    {
        Joueur Albert("albert");
        Joueur Bertrand("bertrand");
        Partie noob(&Albert,&Bertrand);
        Partie pro;
        pro.setJ1(&Albert);
        pro.setJ2(&Bertrand); 
        cout<<(int)Albert.getpartie()[0]<<endl;   
        cout<<(int)&noob<<endl;   
        cout<<"bla"<<endl;
        pro.~Partie();
        noob.~Partie();
        system("PAUSE");
        cout<<"bla"<<endl;
        return EXIT_SUCCESS;   
    }
    Voilà les variables des classes :

    Extrait de Joueur.h :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    // variables de la classe :
    	char * nom; // nom du joueur
    	Partie * partie[5]; // tableau de pointeur sur des parties en cours
    Extrait de Partie.h :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    // variables de la classe :
     
                  char * date; // Pas de classe date pour l'instant
                  Joueur * J1; //2 joueurs distincts
                  Joueur * J2;

    Voici également le code des destructeurs de chacune des 2 classes :

    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
    Joueur :: ~Joueur (){
           delete [] nom;
           for (int i = 0 ; i < 5 ; i++ ){
                 if (partie[i]!=NULL){
                        partie[i]->~Partie();
                 }
           }
    }
     
    Partie :: ~Partie (){ // le destructeur de partie qui détruit le tableau alloué dynamiquement et défait la liaison réciproque des objets
           delete [] date;
           for (int i = 0 ; i < 5 ; i++){ //on va ici parcourir le tableau des parties du joueur 1 a la recherche de la partie en cours          
               if ( J1->getpartie()[i] == this ){
                    J1->minisetpartie(NULL,i); // une fois qu'on l'a trouvé on le supprime                                   
                    }
               }
           for (int i = 0 ; i < 5 ; i++){ // on fait de même pour le deuxième joueur        
               if ( J2->getpartie()[i] == this ){
                    J2->minisetpartie(NULL,i);
                    }
           }
           J1=NULL; // enfin on suprime les liens de la partie vers les joueurs 1
           J2=NULL; // et 2
     
    }
    Problème : le programme affiche les 2 "bla" et plante après : "Ce programme a cessé de fonctionner. Windows recherche une solution au problème"

    Ce problème se produit donc après l'appel aux destructeurs, pourtant il ne se produit pas si je ne les appelle pas... Pourquoi ?

  2. #2
    Invité(e)
    Invité(e)
    Par défaut
    Bonjour

    C'est normal, dans ton code, tu crées deux objets Partie statiques : le programme se chargera de les créer ET de les supprimer.

    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
    class Toto;
    int f1(){ // Cas statique
       Toto obj_1; // OK on ne s'occupe ni de la contruction, ni de la destruction
    }
    int f2(){ // Cas dynamique
       Toto * pObj_2;
       pObj_2 = new Toto();
       delete pObj_2; // OK on s'occupe des deux
    }
    int f3(){
       Toto obj_3; 
       delete & obj_3; // PAS OK : c'est pas notre rôle de libérer l'objet
    }
    int f4(){
       Toto * pObj_4; 
       pObj_4 = new Toto(); // Pas OK, on crée l'objet 4, mais on ne le détruit pas -> fuite mémoire...
    }
    Dans ton cas, tu passes donc deux fois par le destructeur... tu détruis donc deux fois date et les appels à J1->... J2->... se font en fait avec un pointeur NULL en guise de Joueur.

  3. #3
    Membre habitué
    Profil pro
    Inscrit en
    Avril 2008
    Messages
    10
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2008
    Messages : 10
    Par défaut
    Merci, mais la mémoire allouée dans chaque objet (nom du joueur, date de la partie) n'est pas libérée, si ?

  4. #4
    Invité(e)
    Invité(e)
    Par défaut
    Citation Envoyé par perpau07 Voir le message
    Merci, mais la mémoire allouée dans chaque objet (nom du joueur, date de la partie) n'est pas libérée, si ?
    Disons que le destructeur est appelé.
    Après la mémoire est libérée si on demande à la libérer. (Ce qui pose souvent problème lorsqu'on utilise des pointeurs à l'intérieur d'une classe)
    Au passage : page de la FAQ sur les destructeurs
    Pour s'assurer du passage dans les différents constructeurs/destructeurs, il est souvent utile d'ajouter une trace :
    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
    #ifdef _DEBUG
    #define TRACE_CONS cout << "Construction de " << this << endl;
    #define TRACE_DEST cout << "Destruction de " << this << endl;
    #else
    #define TRACE_CONS 
    #define TRACE_DEST 
    #endif
     
    #include <iostream>
    using namespace std;
    class Toto{
    public:
       Toto(){
          TRACE_CONS;
       }
       ~Toto(){
          TRACE_DEST;
       }
    };
    Après, pour éviter tout problème de fuite mémoire avec les chaines de caractères, il est fortement conseilllé en c++ d'utiliser la classe string.

  5. #5
    Membre habitué
    Profil pro
    Inscrit en
    Avril 2008
    Messages
    10
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2008
    Messages : 10
    Par défaut
    Merci bien !

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

Discussions similaires

  1. problème de compilation avec dev c++..
    Par guindilla dans le forum Windows
    Réponses: 1
    Dernier message: 06/11/2007, 16h11
  2. problèmes de compilation avec DEV-CPP
    Par Ben777 dans le forum OpenGL
    Réponses: 8
    Dernier message: 06/04/2007, 13h49
  3. Problème de compilation avec dev c++ : SDLmain
    Par tichau dans le forum Dev-C++
    Réponses: 11
    Dernier message: 24/02/2007, 12h24
  4. Problème de compilation avec dev-c++ pour WIN32 API
    Par ValyGator dans le forum Dev-C++
    Réponses: 2
    Dernier message: 08/01/2007, 14h53
  5. Problème de compilation avec Dev-C++
    Par Rouliann dans le forum Dev-C++
    Réponses: 14
    Dernier message: 14/06/2004, 18h44

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