Partage
  • Partager sur Facebook
  • Partager sur Twitter

Problème avec des include en cascade

    31 décembre 2008 à 1:32:45

    Bonjour, voila mon petit problème.

    Pour la fac, je réalise un projet en C, jusque là, rien de bien compliqué. Seul hic, je me retrouve avec beaucoup de headers, qui s'incluent les uns les autres.

    Ce qui entraine des erreurs de types non déclarées du genre :
    - erreur: expected specifier-qualifier-list before «Case»
    - erreur: les éléments du tableau sont de type incomplet

    J'aimerai donc savoir quelle est la meilleure façon d'organiser le contenu de ses headers pour eviter ces erreurs (qui ne sont pas systematiques).

    Merci

    Edit : code Linux only
    Headers ci-dessous :

    #ifndef CASE_H_INCLUDED
    #define CASE_H_INCLUDED
    
    #include "fourmi.h"
    
    typedef struct
    {
        int x, y;
        Fourmi * fourmilliere;
        FListe habitant;
    } Case;
    
    int nbFourmi( Case * c );
    
    #endif /* CASE_H_INCLUDED */
    

    #ifndef CLICK_H_INCLUDED
    #define CLICK_H_INCLUDED
    
    #include "gui.h"
    #include "zone.h"
    
    typedef struct Click
    {
        int x;
        int y;
        Zone * zone;
    } Click;
    
    Click waitClick( Interface * gui );
    
    #endif /* CLICK_H_INCLUDED */
    

    #ifndef DRAWING_H_INCLUDED
    #define DRAWING_H_INCLUDED
    
    /* Fond */
    #define COULEUR_FOND "White"
    
    
    /* Alertes */
    #define POLICE_ALERTE "-*-courier-bold-*--20-*"
    #define COULEUR_POLICE_ALERTE "Red"
    #define COULEUR_FOND_ALERTE "white"
    #define COULEUR_BORDURE_ALERTE "black"
    
    /* Boutons */
    #define COULEUR_FOND_BOUTON "red"
    #define COULEUR_BORDURE_BOUTON "black"
    #define COULEUR_POLICE_BOUTON "black"
    #define POLICE_BOUTON "-*-courier-bold-*--20-*"
    
    /* Plateau */
    #define COULEUR_FOND_PLATEAU "ForestGreen"
    #define COULEUR_LIGNE_PLATEAU "Blue"
    
    #define COULEUR_FOURMI_ROUGE "Red"
    #define COULEUR_FOURMI_NOIRE "Black"
    
    #define COULEUR_SELECTION "Yellow"
    
    #define POLICE_LISTE_FOURMIS "-adobe-courier-medium-o-normal--10-100-75-75-m-60-iso10646-1"
    #define COULEUR_POLICE_LISTE_FOURMIS "Black"
    
    #define COULEUR_BORDURE_INFO "Black"
    #define COULEUR_FOND_INFO_NEUTRE "White"
    #define COULEUR_FOND_INFO_ROUGE "Red"
    #define COULEUR_FOND_INFO_NOIRE "Grey"
    
    /* include */
    #include "gui.h"
    #include "zone.h"
    #include "monde.h"
    #include "fourmi.h"
    
    /* Prototypes */
    void drawInterface( Interface * interface );
    
    void drawAlerte( char * message, Interface * interface );
    
    /*void drawBouton( Interface * interface , Zone * bouton);*/
    void drawBasePlateau( Interface * gui);
    void drawFond( Interface * interface );
    void drawPlateau( Monde * monde, Interface * interface );
    
    void drawFourmi( Fourmi * fourmi, Interface * interface );
    void drawFourmilliere( Fourmi * fourmi, Interface * interface );
    void drawSelectCase( int x, int y, Interface * interface);
    void drawUnselectCase( int x, int y, Interface * interface);
    
    void drawInfoCase( Case * c, Interface * interface );
    void drawLineFourmi( Fourmi * fourmi, int * offset, Zone * liste_fourmis, Interface * interface );
    void drawListFourmi( Case * c, Interface * interface );
    #endif /* DRAWING_H_INCLUDED */
    

    #ifndef FOURMI_H_INCLUDED
    #define FOURMI_H_INCLUDED
    
    #define ROUGE 'R'
    #define NOIRE 'N'
    #define INDETERMINE '\0'
    
    #define OUVRIERE 'o'
    #define REINE 'r'
    #define FOURMILLIERE 'f'
    
    #define TOUVRIERE 3
    #define TREINE 6
    
    typedef struct four
    {
        char couleur;
        char genre;
        int posx, posy;
        int destx, desty;
        int produit, temps;
        struct four * fsuiv;
        struct four * fprec;
        struct four * vsuiv;
        struct four * vprec;
    } Fourmi, *FListe;
    
    #include <stdlib.h>
    #include "monde.h"
    
    Fourmi * newFourmi( char genre, int posx, int posy, Fourmi * parent );
    
    void killFourmi( Fourmi * fourmi, Monde * monde );
    void killFourmilliere( Fourmi * fourmi, Monde * monde );
    
    void attacheFourmi(Fourmi * fourmi, Monde * monde);
    void detacheFourmi(Fourmi * fourmi, Monde * monde);
    
    void immobiliseFourmi( Fourmi * fourmi);
    
    void setConstruction( Fourmi * fourmilliere, char genre );
    Fourmi * updateConstruction( Fourmi * fourmilliere, Monde * monde);
    
    #endif /* FOURMI_H_INCLUDED */
    

    #ifndef GUI_H_INCLUDED
    #define GUI_H_INCLUDED
    
    #define TAILLE_CASE 10
    
    #include <MlvTypeC.h>
    #include <MlvProcC.h>
    #include <stdlib.h>
    #include <stdio.h>
    
    typedef MlvStruct Fenetre;
    
    typedef struct Interface Interface;
    
    #include "monde.h"
    #include "zone.h"
    #include "drawing.h"
    
    struct Interface
    {
        Fenetre * fenetre;
    
        struct ListeZone * zoneActive;
        struct ListeZone * zoneInactive;
    };
    
    Interface * setInterface( void );
    void initZones( Interface * interface );
    
    void delInterface( Interface * interface );
    
    
    
    void printInterface( Interface * interface);
    void alerte( char * message, Interface * interface );
    
    #endif /* GUI_H_INCLUDED */
    

    #ifndef MAIN_H_INCLUDED
    #define MAIN_H_INCLUDED
    
    #include <stdio.h>
    #include <stdlib.h>
    #include "monde.h"
    #include "gui.h"
    #include "click.h"
    #include "zone.h"
    
    
    
    /**
     *  \brief Les differents etats de la partie
     */
    typedef enum
    {
        CONTINUER,
        EN_COURS,
        VICTOIRE_NOIRE,
        VICTOIRE_ROUGE,
        VICTOIRE_NUL
    } Score;
    
    void main_play( Fenetre * fenetre );
    int tour( char joueur_actif, Monde * monde, Interface * interface );
    Case * selectCase( Click click, Monde * monde, Interface * interface );
    
    #endif /* MAIN_H_INCLUDED */
    

    #ifndef MONDE_H_INCLUDED
    #define MONDE_H_INCLUDED
    
    typedef struct Monde Monde;
    
    #include "case.h"
    #include "fourmi.h"
    
    #define X 60
    #define Y 40
    #define X_START_NOIR 10
    #define Y_START_NOIR 10
    #define X_START_ROUGE 50
    #define Y_START_ROUGE 30
    
     struct Monde
    {
        Case plateau[X][Y];
        FListe Rouge;
        FListe Noir;
    };
    
    Monde * newWorld(void);
    void delWorld(Monde * monde);
    
    
    #endif /* MONDE_H_INCLUDED */
    

    #ifndef BOUTON_H_INCLUDED
    #define BOUTON_H_INCLUDED
    
    #include <stdarg.h>
    
    typedef enum
    {
        /* général */
        QUITTER,
        CHARGER,
        SAUVEGARDER,
        FIN_TOUR,
        PLATEAU,
    
        /* infos case */
        INFO_CASE,
        LISTE_FOURMIS,
    
        /* actions fourmis */
        DEPLACEMENT,
        SUPPRIMER,
        IMMOBILISER,
        PRODUCTION_OUVRIERE,
        PRODUCTION_REINE
    
    } IdZone;
    
    typedef struct Zone
    {
        int x_start;
        int y_start;
        int taille_x;
        int taille_y;
        char * nom;
        IdZone zone;
    } Zone;
    
    typedef struct ListeZone
    {
        Zone * zone;
        struct ListeZone * suivant;
        struct ListeZone * precedent;
    } ListeZone;
    
    #include "gui.h"
    #include "monde.h"
    
    Zone * createZone( int x, int y, int largeur, int hauteur, char * nom, IdZone zone );
    void setZoneActive( Interface * interface, int nombreZone, ...);
    void setZoneInactive( Interface * interface, int nombreZone, ...);
    
    int AddListeZone( Zone * zone, ListeZone ** listeZone);
    Zone * findZone( IdZone idZone, ListeZone * listeZone );
    
    void supprimerListeZone( ListeZone ** listeZone );
    void supprimerZone( Zone * zone );
    
    int isInside( int x, int y, Zone * zone);
    
    #endif
    

    • Partager sur Facebook
    • Partager sur Twitter
      31 décembre 2008 à 1:46:54

      Citation : Floooder

      beaucoup de headers,



      A mon avis, si tu veux soulager les personnes qui testeront ton code tu devrais leur épagner le copier-coller des 8 fichiers d'en-tête et leur proposer un lien de téléchargement.
      • Partager sur Facebook
      • Partager sur Twitter
        31 décembre 2008 à 1:51:15

        Ok, voici le lien svn :

        http://svn.assembla.com/svn/Projet-fourmis/

        Mais malheureusement pour tester le programme, ca risque de ne pas le faire, il faut installer la librairie graphique de l'université -_-'

        Le code source de la lib est fournie avec, mais il faut utiliser le script install.sh en lui fournissant le dossier d'install en parametre. Ah, et il faut aussi la libX11-dev ^__^
        • Partager sur Facebook
        • Partager sur Twitter
          31 décembre 2008 à 19:49:22

          Donc si vous avez une solution qui evitent ce genre de soucis, ca serrait un super cadeau pour la nouvelle année.

          Jusqu'a maintenant, je bidouillais l'ordre des headers, mais une methode systematique me serrait du plus grand secours
          (avec les gardes d'inclusion multiple, difficile de remonter l'ordre exact d'inclusion des headers, et surtout que ca ne pose pas de problème pour compiler chaque .c)

          Bonne année a tous ;)
          • Partager sur Facebook
          • Partager sur Twitter
            31 décembre 2008 à 20:12:34

            Citation : Floooder

            Donc si vous avez une solution qui evitent ce genre de soucis, ca serrait un super cadeau pour la nouvelle année.


            Le principe est de définir avant d'utiliser. Essaye de réduire le code à un exemple simple qui montre le problème.

            Il y a certaines choses impossibles, comme la définition croisée de structures (pb de poule et d'œuf).
            struct a;
            {
               struct b b; /* taille de b inconnue ... */
            };
            
            struct b;
            {
               struct a a;
            };
            

            évidemment, en plus ça n'a aucun sens... Mais si ce sont des pointeurs, pas de problème.
            struct a;
            {
               struct b *pb;
            };
            
            struct b;
            {
               struct a a;
            };
            

            • Partager sur Facebook
            • Partager sur Twitter
            Music only !
              2 janvier 2009 à 1:05:18

              Voila un code simple qui montre l'erreur :

              #ifndef MONDE_H_INCLUED
              #define MONDE_H_INCLUED
              
              #include "fourmi.h"
              #include "case.h"
              
              typedef struct monde
              {
                 Case [10];
                 fourmi * liste;
              } monde;
              
              #endif
              

              #ifndef CASE_H_INCLUED
              #define CASE_H_INCLUED
              
              #include "fourmi.h"
              
              typedef struct Case
              {
                 fourmi * list;
              }Case;
              
              #endif
              

              #ifndef FOURMI_H_INCLUED
              #define FOURMI_H_INCLUED
              
              #include "monde.h"
              #include "case.h"
              
              typedef struct fourmi
              {
                 int val;
              } fourmi;
              
              int func(fourmi * f, Case * c);
              int fonc2(fourmi * f, monde * m);
              
              #endif
              


              Ceci dit, j'ai peut être la solution, definir les structures dans un headers séparé des fonctions...
              • Partager sur Facebook
              • Partager sur Twitter
                2 janvier 2009 à 1:55:33

                Citation : Floooder

                Voila un code simple qui montre l'erreur :

                #ifndef MONDE_H_INCLUED
                #define MONDE_H_INCLUED
                
                #include "fourmi.h"
                #include "case.h"
                
                typedef struct monde
                {
                   Case [10];
                   fourmi * liste;
                } monde;
                
                #endif
                


                <...>


                C'est quoi Case [10]; Ca n'a aucun sens... Il faut un type...

                Quand c'est tordu, essayer déjà sans les typedef, c'est moins rigoureux et ça marche pareil :

                Ceci fonctionne :
                #include "fourmi.h"
                
                int main (void)
                {
                   return 0;
                }
                

                avec
                #ifndef FOURMI_H_INCLUED
                #define FOURMI_H_INCLUED
                
                #include "monde.h"
                #include "case.h"
                
                struct fourmi
                {
                   int val;
                };
                
                int func(struct fourmi * f, struct Case * c);
                int fonc2(struct fourmi * f, struct monde * m);
                
                #endif
                

                #ifndef MONDE_H_INCLUED
                #define MONDE_H_INCLUED
                
                #include "fourmi.h"
                #include "case.h"
                
                struct monde
                {
                   struct Case Case[10];
                   struct fourmi *liste;
                };
                
                #endif
                

                #ifndef CASE_H_INCLUED
                #define CASE_H_INCLUED
                
                #include "fourmi.h"
                
                struct Case
                {
                   struct fourmi * list;
                };
                
                #endif
                

                • Partager sur Facebook
                • Partager sur Twitter
                Music only !
                  2 janvier 2009 à 2:02:37

                  Ouip, erreur d'inatention pour Case[10] ;) c'etait bien evidement Case map[10] que j'avais voulu ecrire...

                  Par contre ceci ne fonctionne pas...

                  Ca marche si tu inclu "fourmi.h" dans le .c (ie fourmi.c), mais pas si tu inclu "case.h" (ie case.c) ou "monde.h" (ie monde.c)
                  • Partager sur Facebook
                  • Partager sur Twitter
                    2 janvier 2009 à 3:30:38

                    Citation : Floooder

                    Ouip, erreur d'inatention pour Case[10] ;) c'etait bien evidement Case map[10] que j'avais voulu ecrire...

                    Par contre ceci ne fonctionne pas...

                    Ca marche si tu inclu "fourmi.h" dans le .c (ie fourmi.c), mais pas si tu inclu "case.h" (ie case.c) ou "monde.h" (ie monde.c)


                    J'ai compris. En fait, la hiérarchie est correcte :

                    fourmi
                    Case
                    monde

                    Il n'y a pas de dépendance croisée, on peut donc bien avoir 3 headers séparés et liés par inclusion.

                    ce qui met le bazar, ce sont les prototypes qui sont mal placés. Il doivent être placés là où on connait les structures, c'est à dire que fonc() doit être dans case.h et fonc2() dans monde.h.

                    ce qui donne :
                    #include "monde.h"
                    
                    int main (void)
                    {
                       struct fourmi f;
                       struct Case c;
                       struct monde m;
                    
                       case_func (&f, &c);
                       monde_func (&f, &m);
                    
                       return 0;
                    }
                    

                    #ifndef FOURMI_H_INCLUED
                    #define FOURMI_H_INCLUED
                    
                    struct fourmi
                    {
                       int val;
                    };
                    
                    #endif
                    

                    #ifndef CASE_H_INCLUED
                    #define CASE_H_INCLUED
                    
                    #include "fourmi.h"
                    
                    struct Case
                    {
                       struct fourmi *list;
                    };
                    
                    int case_func (struct fourmi *f, struct Case *c);
                    
                    #endif
                    

                    #ifndef MONDE_H_INCLUED
                    #define MONDE_H_INCLUED
                    
                    #include "case.h"
                    
                    struct monde
                    {
                       struct Case map[10];
                       struct fourmi *liste;
                    };
                    
                    int monde_fonc (struct fourmi *f, struct monde *m);
                    
                    #endif
                    

                    #include "fourmi.h"
                    

                    #include "case.h"
                    
                    int case_func(struct fourmi * f, struct Case * c)
                    {
                       return 0;
                    }
                    

                    #include "monde.h"
                    
                    int monde_func (struct fourmi *f, struct monde *m)
                    {
                       return 0;
                    }
                    

                    Il suffisait de respecter la hiérarchie strictement.

                    • Partager sur Facebook
                    • Partager sur Twitter
                    Music only !
                      4 janvier 2009 à 1:56:21

                      Si tu regardes mon code source d'origine (le gros) tu verra que les fonctions etaient dans les headers logiques par rapport a ce qu'elles sont censés faire... maintenant c'est vrai que c'est ce qui posait problème

                      Ceci dit, j'ai résolu le problème en mettant les définitions de structure dans des headers séparés.

                      Enfin merci pour le coup de main

                      Je mettrai a dispo le code final une fois que ca serra fini ;)
                      • Partager sur Facebook
                      • Partager sur Twitter
                        4 janvier 2009 à 10:21:28

                        Citation : Floooder

                        Si tu regardes mon code source d'origine (le gros) tu verra que les fonctions etaient dans les headers logiques par rapport a ce qu'elles sont censés faire... maintenant c'est vrai que c'est ce qui posait problème

                        Ceci dit, j'ai résolu le problème en mettant les définitions de structure dans des headers séparés.


                        Je ne comprends pas. J'ai donné une solution qui fonctionne et qui est logique et organisée... Pourquoi faire autrement ?
                        • Partager sur Facebook
                        • Partager sur Twitter
                        Music only !

                        Problème avec des include en cascade

                        × Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
                        × Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
                        • Editeur
                        • Markdown