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 :

compilation et ex�cution ok, mais erreur sous gdb


Sujet :

C++

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

    Informations forums :
    Inscription : Mai 2008
    Messages : 10
    Par d�faut compilation et ex�cution ok, mais erreur sous gdb
    Bonjour.
    Je cherche � comprendre pourquoi mon programme pose probl�me � gdb. La compilation se d�roule sans erreur et le programme s'ex�cute normalement, mais gdb me renvoie un "Debugger finished with status 1" et les points d'arr�t ne fonctionnent pas.

    classe.hpp
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    #ifndef CLASSE_HPP
    #define CLASSE_HPP
    #include <vector>
     
    const int               array[] = {1, 2, 3, 4};
    const std::vector<int>  vect (array, array + 4);
     
    class MaClasse
    {
        MaClasse();
        ~MaClasse();
        std::vector<int>*    pVect;
    };
    #endif  //CLASSE_HPP
    classe.cpp
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    #include "classe.hpp"
     
    MaClasse::MaClasse()
    {
        pVect = new std::vector<int>(4);
    }
     
    MaClasse::~MaClasse()
    {
        delete pVect;
    }
    main.cpp
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    #include <iostream>
    #include "classe.hpp"
     
    int main()
    {
        std::cout << "Un simple test..." << std::endl;
        return 0;
    }
    Les sources originales ont �t� "all�g�es" pour �tre pr�sent�es sur le forum, ce qui explique l'inutilit� des variables globales.


    Le probl�me disparait si je regroupe tout le code dans un m�me fichier. M�me chose si je supprime les deux variables globales (array et vect dans classe.hpp). Ou bien encore en modifiant l'allocation dynamique dans le constructeur :

    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
     
    pVect  = new std::vector<int>(4); // erreur
    pVect  = new std::vector<int>; // ok
    Voici la copie de la console de gdb :
    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
     
    Building to ensure sources are up-to-date
    Build succeeded
    Selecting target: 
    Debug
    Adding source dir: E:\developpement\CodeBlocks\projet\vecttest\
    Adding source dir: E:\developpement\CodeBlocks\projet\vecttest\
    Adding file: bin\Debug\vecttest.exe
    Starting debugger: 
    done
    Registered new type: wxString
    Registered new type: STL String
    Registered new type: STL Vector
    Setting breakpoints
    Debugger name and version: GNU gdb 6.8
    Child process PID: 3060
    Debugger finished with status 1

    J'ai remarqu� que le log d�taill� de gdb se termin� par un message inhabituel. A toute fin utile, j'en fournis les derni�res lignes :
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
     
    > run
    gdb: win32_init_thread_list
    This application has requested the Runtime to terminate it in an unusual way.
    Please contact the application's support team for more information.
    [New thread 3252.0x914]
    J'utilise gdb 6.8 avec code::blocks � jour, le tout sous XP.

    Le probl�me vient-il de mon code ou d'une mauvaise configuration de mingw32? Si quelqu'un peut m'apporter quelques �claircissements, je suis preneur parce que l�, je s�che.

    Merci d'avance.

  2. #2
    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, et bienvenue sur le forum.

    Retiens toujours qu'une compilation sans erreur ne signifie nullement que ton code est correct: cela signifie seulement que le compilateur n'a rien rencontr� qui d�roge aux r�gles qu'il suit

    De mani�re g�n�rale, il faut �viter l'allocation dynamique d'objet et le recours aux pointeurs si tu n'as pas absolument besoin des possibilit�s qu'ils offrent (entre autres, au niveau du polymorphisme, ou quand le "contenu" doit survire � la destruction du "contenant").

    Et c'est encore plus vrai avec les classes de la S(T)L

    L'id�al, pour le membre que tu nomme dans ton exemple pVect est donc:
    d'utiliser une valeur plut�t qu'un pointeur
    d'utiliser la liste d'initialisation pour initialiser le membre

    Cela donne au final un code proche de
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    //dans classe_hpp
    class MaClasse
    {
        MaClasse();
        ~MaClasse();
        std::vector<int>    m_vect;
    };
    //dans classe_cpp
    MaClasse::MaClasse():m_vect(vect)
    {
    }
    MaClasse::~MaClasse()
    {
    }
    En effet, la port�e des variables fait que la variable est automatiquement d�truite lorsque l'on quitte la port�e dans laquelle elle a �t� d�clar�e, et, au niveau des classes, les membres sont automatiquement cr��s lorsque le constructeur est appel� (lorsque l'on d�clare une nouvelle instance du type de la classe) et d�truits lorsque le destructeur est appel� (lorsque l'instance en question est d�truite).

    cela signifie que tu que tu as la certitude que, dans le code suivant
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    void fonction()
    {
        MaClasse c1;   //(1)
        for(int i=0; i<10; ++i)
        {
             MaClasse c2;  //(2)
             /*...*/
        }  //(3)
        /*...*/
    }  //(4)
    • les membres de c1 sont construits en 1 et d�truits en 4
    • la variable c2 est construite en 2 et syst�matiquement d�truite en 3 (et ce � chaque passage dans la boucle)
    • les membres de c2 sont donc construit en 2 et d�tuits en 3

    Ceci �tant fix�, on pourrait encore te faire valoir:
    • que les variables globales, c'est mal
    • qu'avec la premi�re variable globale Array, il devient inutile de rajouter une variable vect
    • qu'il est sans doute pr�f�rable de rendre les membres de ta classe (ici, m_vect, une fois les modifications apport�es) priv�s ou port�g�s, de mani�re � �viter de briser l'encapsulation.
    • que l'on est tous d'accord pour "rab�cher" la fameuse rengaine "�vitez les tableaux C style et pr�f�rez leur les classes du C++"

    Cependant, il ne faut pas se faire plus catholique que le pape non plus - pour ce qui concerne les tableaux- et, si tu sais pertinemment qu'un tableau n'aura jamais qu'un nombre r�duit et bien connu � l'avance d'�l�ments, l'utilisation d'un tableau C style non allou� dynamiquement peut tr�s bien faire l'affaire.

    Ainsi, si tu es sur que ton tableau d'entiers ne contiendra jamais que 4 entiers, ni plus, ni moins, tu peux parfaitement envisager de le d�clarer sous la forme toute simple de
    En ce qui concerne les variables globales, on conseille plut�t d'avoir recours � ce que l'on appelle les membres de classe (par opposition aux membres d'instance).

    Ce sont des membres "particuliers" qui font partie d'une classe donn�e, mais qui
    1. ne d�pendent pas d'une instance particuli�re de la classe
    2. sont partag�s par l'ensemble des instances de la classe

    Pour d�clarer un membre de classe, il suffit de faire pr�c�der sa d�claration au sein de la classe par le mot cl� static sous une forme proche de
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    MaClass
    {
        public:
            MaClasse();
            ~MaClasse();
            static /* const */ int array[4];
            std::vector<int> m_vect;
    };
    (tu trouveras la r�ponse � la plupart des questions que tu peux te poser sur les membres statiques dans la partie de la FAQ qui leur est r�serv�e )
    et, si le seul tableau d'entiers dont tu as besoin est, justement, le tableau statique, tu peux donc sans aucun probl�me supprimer le membre m_vect
    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

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

    Informations forums :
    Inscription : Mai 2008
    Messages : 10
    Par d�faut
    Bonjour koala01 et merci pour tes explications, claires et d�taill�es. A vrai dire je n'en esp�rais pas autant.

    Tes critiques pertinentes sur mon code, en-dehors de mon probl�me, sont les bienvenues et j'en prends note. Elles sont autant d'occasions de prendre de bonnes habitudes.

    Si j'ai choisi les vecteurs � la place des tableaux, c'est avant tout pour profiter des m�thodes et algorithmes de la STL, cela m'�vite de r�inventer la roue. De plus, c'est l'occasion de me faire la main sur les vecteurs.

    Quant � l'allocation dynamique, elle me semblait indispensable pour pouvoir faire varier la taille du vecteur au fil du temps. Si j'ai bien compris, cette variation peut tout aussi bien s'appliquer � m_vect. Je vais me documenter sur ce point pr�cis avant d'aller plus loin.

    Au sujet des membres de classe, c'est la solution qu'il me fallait. J'avais d�j� abord� cette notion dans des cours mais j'en ai enfin un cas d'utilisation pratique.

    Je vais donc revoir ma copie en tenant compte de tes remarques .

  4. #4
    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
    En fait, il faut bien comprendre que le d'une classe est de cacher les "d�tails d'impl�mentation" (dans le cas de la classe vector, on peut citer le fait qu'il y a surement un T* tab quelque part ) et d'exposer les comportements "qui vont bien" pour la classe en question.

    Ainsi, la classe vector propose plusieurs m�thodes parmis lesquelles push_back, push_front et insert dont on se doute qu'elles s'occupent de la gestion dynamique du membre tab (avec (r�)allocation en cas de besoin)

    De la m�me mani�re, on se doute que la m�thode clear ou que le destructeur va se charger de la d�sallocation de la m�moire allou�e � tab

    C'est la raison pour laquelle il est conseill� d'utiliser, tout simplement, un membre non pointeur quand tu utilise la classe std::vector et de pr�f�rer, en cas de n�cessit�, le passage par r�f�rence �... l'utilisation d'un pointeur
    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

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

    Informations forums :
    Inscription : Mai 2008
    Messages : 10
    Par d�faut
    J'ai apport� les modifications propos�es, toutefois mon probl�me avec gdb restait entier : "Debugger finished with status 1" et points d'arr�t inefficaces.

    J'ai quand m�me fini par trouver une solution. D'apr�s le log de gdb, le d�bogueur plante. J'ai donc utilis� gdb en ligne de commande, et isol� la commande � l'origine du plantage : catch thrown. La solution sous Code::Blocks consiste donc � d�cocher "Catch C++ exceptions" dans Settings->Compiler and debugger...->Debugger settings. A pr�sent, �a roule

    Merci encore � koala01 pour ses conseils.

+ R�pondre � la discussion
Cette discussion est r�solue.

Discussions similaires

  1. R�ponses: 1
    Dernier message: 15/03/2014, 15h10
  2. ca fonctionne mais erreur compilation d�claration sub
    Par petitours dans le forum VBA Access
    R�ponses: 2
    Dernier message: 19/12/2007, 18h30
  3. [PHP-JS] Erreur sous ie mais pas sous ff
    Par ozzmax dans le forum Langage
    R�ponses: 6
    Dernier message: 10/07/2007, 17h04
  4. R�ponses: 2
    Dernier message: 20/03/2007, 11h50
  5. erreur de requete sous php mais pas sous mysql
    Par kenny49 dans le forum Requ�tes
    R�ponses: 21
    Dernier message: 28/06/2006, 16h36

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