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 avec qsort (structure complexe)


Sujet :

C

  1. #1
    Futur Membre du Club
    Femme Profil pro
    Formateur en informatique
    Inscrit en
    Décembre 2012
    Messages
    11
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Formateur en informatique

    Informations forums :
    Inscription : Décembre 2012
    Messages : 11
    Points : 6
    Points
    6
    Par défaut Problème avec qsort (structure complexe)
    Bonjour,

    Après plusieurs heures de recherche toujours pas de solution, je me rends compte que je ne suis pas aussi à l'aise avec les pointeurs que je ne pensais..

    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
     
    /* 
       Un fichier a :
       - un nom 
       - un descripteur de fichier
       - un tableau de fichier ou NULL si ce n'est pas un répertoire
    */
    struct file {
      char* name;
      int fd;
      struct t_files* son;
    };
     
    /*
      un tableau de fichiers 
      - sa taille 
      - un tableau de pointeur vers des fichiers 
    */
    struct t_files {
      struct file** t;
      int size;
    };
    Je souhaite trier selon le nom, pour cela j'ai :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    int struct_cmp_by_name(const void* a, const void*b ){
      struct file *ia = (struct file*)a;
      struct file *ib =  (struct file*)b;
      return strcmp(ia->name, ib->name);
    }
     
    int main(void) {
      struct t_files* res;
      /* fonction pour remplissage res (aucun problème de ce côté) */
      qsort (?, ??, ???, struct_cmp_by_name);
    }
    J'ai tenté de mettre différents paramètres sans succès.

    Merci d'avance pour votre aide

  2. #2
    Modérateur

    Avatar de Bktero
    Homme Profil pro
    Développeur en systèmes embarqués
    Inscrit en
    Juin 2009
    Messages
    4 481
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 36
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur en systèmes embarqués

    Informations forums :
    Inscription : Juin 2009
    Messages : 4 481
    Points : 13 679
    Points
    13 679
    Billets dans le blog
    1
    Par défaut
    Pourquoi souhaites-tu faire un tableau de structures puisque cette structure contient déjà un tableau ?

  3. #3
    Futur Membre du Club
    Femme Profil pro
    Formateur en informatique
    Inscrit en
    Décembre 2012
    Messages
    11
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Formateur en informatique

    Informations forums :
    Inscription : Décembre 2012
    Messages : 11
    Points : 6
    Points
    6
    Par défaut
    parce que j'en ai besoin pour stocker dedans quelques fichiers ! mais ce n'est pas ça ma question, ce que je veux savoir ,c'est comment faire le tri de " res " selon le " name "

  4. #4
    Modérateur

    Avatar de Bktero
    Homme Profil pro
    Développeur en systèmes embarqués
    Inscrit en
    Juin 2009
    Messages
    4 481
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 36
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur en systèmes embarqués

    Informations forums :
    Inscription : Juin 2009
    Messages : 4 481
    Points : 13 679
    Points
    13 679
    Billets dans le blog
    1
    Par défaut
    Si tu veux stocker quelques fichiers dedans, pourquoi un tableau de tableaux et non simplement un tableau ? En fait, ça a à avoir avec ta question parce que le premier paramètre de qsort est le tableau à trier :
    Or, si res est un tableau de structures contenant chacune un tableau, il faut que tu lui précises laquelle ces structures il doit trier. En effet, ta fonction de comparaison compare deux fichiers, qsort te servira donc à trier un tableau de fichier. C'est le premier paramètre. Le second sera le nombre d'éléments de ce tableau (la structure le contient). Le troisième est la taille d'un élément (sizeof pourra t'aider).

  5. #5
    Futur Membre du Club
    Femme Profil pro
    Formateur en informatique
    Inscrit en
    Décembre 2012
    Messages
    11
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Formateur en informatique

    Informations forums :
    Inscription : Décembre 2012
    Messages : 11
    Points : 6
    Points
    6
    Par défaut
    je voudrais trier le tableau qui est dans "res " c'est à dire : res->t
    selon le champ "name", c'est pour un projet, j'utilise cette structure dans mes différentes fonctions (environ 1000 lignes de code) sans changer la structure, je peux réussir à faire appel à qsort ?


    Merci pour votre aide

  6. #6
    Futur Membre du Club
    Femme Profil pro
    Formateur en informatique
    Inscrit en
    Décembre 2012
    Messages
    11
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Formateur en informatique

    Informations forums :
    Inscription : Décembre 2012
    Messages : 11
    Points : 6
    Points
    6
    Par défaut
    c'est la structure qui me semblait la plus évident, un tableau de fichiers c'est la taille du tableau et un pointeur vers un tableau de pointeurs, je vois Bktero ce que tu veux dire, j'ai testé la fonction qsort sur plusieurs structures plus simples, avec différentes fonctions de comparaisons pour bien comprendre mais pour lui donner le bon argument pour ma structure là c'est plus compliqué.. comment lui dire ce qui est un tableau de fichiers ? je pensais que res->t était correct, mais non..

  7. #7
    Futur Membre du Club
    Femme Profil pro
    Formateur en informatique
    Inscrit en
    Décembre 2012
    Messages
    11
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Formateur en informatique

    Informations forums :
    Inscription : Décembre 2012
    Messages : 11
    Points : 6
    Points
    6
    Par défaut Simplification de la structure
    Je viens de finir de corriger les erreurs, je ne savais pas que mon struct file** t était inutile, y a t'il une différence ?

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    struct t_files {
      struct file* t;
      int size;
    };
    j'ai donc fais appel à
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    qsort (res->t, sizeof res->t / sizeof *res->t, sizeof *res->t, struct_cmp_by_name);
    mais le tableau n'était pas trié, en cherchant j'ai trouvé que

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
        printf("%d\n", sizeof res->t / sizeof *res->t);
    donnait 0 sauf erreur de ma part, un problème dans les arguments..

  8. #8
    Inactif  


    Homme Profil pro
    Doctorant sécurité informatique — Diplômé master Droit/Économie/Gestion
    Inscrit en
    Décembre 2011
    Messages
    9 012
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 31
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Doctorant sécurité informatique — Diplômé master Droit/Économie/Gestion
    Secteur : Enseignement

    Informations forums :
    Inscription : Décembre 2011
    Messages : 9 012
    Points : 23 145
    Points
    23 145
    Par défaut
    Bonjour,

    void qsort (void *base, size_t nmemb, size_t size,

    int (*compar)(const void *, const void *));
    base = ton tableau
    nmemb = nombre d'élément
    size = taille d'un élément
    compar = pointeur sur une fonction de comparaison d'élément.

    Donc :
    qsort (res->t, res->size, sizeof *res->t, struct_cmp_by_name);
    Ne pas oublier qu'un sizeof d'un pointeur donne la taille du pointeur (4 pour architecture 32 bits).

  9. #9
    Membre expérimenté Avatar de plxpy
    Homme Profil pro
    Ingénieur géographe
    Inscrit en
    Janvier 2009
    Messages
    792
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 59
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Ingénieur géographe
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Janvier 2009
    Messages : 792
    Points : 1 481
    Points
    1 481
    Par défaut
    Une remarque sur la forme mais qui me parait essentielle surtout si - je me base sur ton statut "formateur en informatique" - tu prépares un cours.

    Mettre, même en commentaire, :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    /*
      un tableau de fichiers 
      - sa taille 
      - un tableau de pointeur vers des fichiers 
    */
    pour enchainer de suite sur (je me contrefiche de la double *)

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    struct t_files {
      struct file** t;
      int size;
    };
    c'est-à-dire la définition d'une structure est à bannir (sauf à vouloir faire grossir les rangs, déjà bien fournis, des posteurs du forum C qui mélangent tout)
    "La simplicité ne précède pas la complexité, elle la suit." - Alan J. Perlis
    DVP ? Pensez aux cours et tutos, ainsi qu'à la FAQ !

  10. #10
    Membre confirmé
    Avatar de Captain'Flam
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Février 2011
    Messages
    273
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

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

    Informations forums :
    Inscription : Février 2011
    Messages : 273
    Points : 455
    Points
    455
    Billets dans le blog
    1
    Par défaut
    Bonjour étudiante6, je trouve que tu te compliques un peu la vie avec tes structures et autres **.
    Voici une petite version "simplifiée" :
    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
    typedef struct
        {
        const char * name ;
        int fd ;
        } file ;
     
    int struct_cmp_by_name ( const void * a, const void * b )
        {
        file *ia = (file*)a ;
        file *ib = (file*)b ;
        return strcmp( ia->name,ib->name ) ;
        }
     
    void foo ( void )
        {
        file t [5] = {{ "le",5 },{ "petit",6 },{ "chat",8 },{ "est",45 },{ "mort",51 }} ;
        qsort( t,5,sizeof( file ),struct_cmp_by_name ) ;
        }
    La fonction foo te montre qu'on peut se passer de t_files.
    De plus, n'oublie pas qu'en C (!= C++) typedef struct permet d'éviter de rajouter struct devant chaque utilisation du type.

    plxpy, je ne suis pas sûr de comprendre le sens de ta remarque :
    Tu veux dire que c'est mal d'annoncer qu'on va déclarer un tableau et de finalement déclarer une structure ?
    Captain'Flam
    anciennement Sopsag, aka Hadrien
    Win seven x64 & Win 10 / Visual 2017 / Python 2.7 / Eclipse

  11. #11
    Membre expérimenté Avatar de plxpy
    Homme Profil pro
    Ingénieur géographe
    Inscrit en
    Janvier 2009
    Messages
    792
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 59
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Ingénieur géographe
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Janvier 2009
    Messages : 792
    Points : 1 481
    Points
    1 481
    Par défaut
    Citation Envoyé par Captain'Flam
    Tu veux dire que c'est mal d'annoncer qu'on va déclarer un tableau et de finalement déclarer une structure ?
    C'est exactement ça.
    "La simplicité ne précède pas la complexité, elle la suit." - Alan J. Perlis
    DVP ? Pensez aux cours et tutos, ainsi qu'à la FAQ !

  12. #12
    Membre confirmé
    Avatar de Captain'Flam
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Février 2011
    Messages
    273
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

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

    Informations forums :
    Inscription : Février 2011
    Messages : 273
    Points : 455
    Points
    455
    Billets dans le blog
    1
    Par défaut
    Alors je suis super d'accord avec toi !
    Il vaut mieux pas de commentaire du tout qu'un commentaire qui ne correspond pas !
    Ex : copier/coller d'une déclaration + modification de la déclaration + commentaire pas mis à jour
    --> au bout de quelques cas de ce genre, et tu ne sais plus ce qu'il faut croire : le code (qui peut être buggé) ou le commentaire.
    Captain'Flam
    anciennement Sopsag, aka Hadrien
    Win seven x64 & Win 10 / Visual 2017 / Python 2.7 / Eclipse

  13. #13
    Expert éminent sénior
    Avatar de Sve@r
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Février 2006
    Messages
    12 685
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Oise (Picardie)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Février 2006
    Messages : 12 685
    Points : 30 974
    Points
    30 974
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par étudiante6 Voir le message
    Je viens de finir de corriger les erreurs, je ne savais pas que mon struct file** t était inutile, y a t'il une différence ?

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    struct t_files {
      struct file* t;
      int size;
    };
    Bonsoir
    Oui il y a une différence. Là tu déclares une structure apte à gérer un tableau de "struct file" donc un tableau de fichiers selon ta conception. Alors qu'au premier coup, tu déclarais une structure apte à gérer un tableau de pointeurs, chaque pointeur pouvant, lui, être le début d'un tableau. Donc pour simplifier tu avais créé une structure faite pour gérer un tableau de tableaux (ce qui est la représentation C d'un tableau 2D).
    En l'état, ton nouveau code est mieux construit et cohérent avec ton problème. Toutefois, si tu prenais de suite l'habitude de nommer tes structures "s_" et tes types "t_" cela te simplifierait la relecture (et à nous aussi) de ton code et éviterait de confondre "file" (le type) et "file" (le fichier)...
    Mon Tutoriel sur la programmation «Python»
    Mon Tutoriel sur la programmation «Shell»
    Sinon il y en a pleins d'autres. N'oubliez pas non plus les différentes faq disponibles sur ce site
    Et on poste ses codes entre balises [code] et [/code]

  14. #14
    Futur Membre du Club
    Femme Profil pro
    Formateur en informatique
    Inscrit en
    Décembre 2012
    Messages
    11
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Formateur en informatique

    Informations forums :
    Inscription : Décembre 2012
    Messages : 11
    Points : 6
    Points
    6
    Par défaut Remerciments
    Merci à tous ! Ca n'a jamais été un si grand bonheur de voir le résultat d'un tri !
    Encore plus que si je l'avais écris moi même pour vous dire.
    Et puis vos explications sont très clairs, j'ai très bien compris, je ne pouvais imaginer que le problème venait de ma structure !


    Au-delà de l'erreur au niveau du commentaire lui même, il ne faut jamais mettre de commentaire à une structure si je comprends bien ?
    C'est vrai pour le typedef struct, merci !

    Sve@r par contre je ne suis pas sûre d'avoir compris pour la convention, pour moi le "t_" était pour tableau, donc quand c'est pour une structure la convention veut qu'on commence par "s_" ?

    Merci donc à Captain'Flam, Sve@r, plxpy, Neckara, Bktero[/B] pour votre temps !

  15. #15
    Membre confirmé
    Avatar de Captain'Flam
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Février 2011
    Messages
    273
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

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

    Informations forums :
    Inscription : Février 2011
    Messages : 273
    Points : 455
    Points
    455
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par étudiante6 Voir le message
    il ne faut jamais mettre de commentaire à une structure si je comprends bien ?
    Arrrrgl !
    Bien sûr que siiiii ! il faut mettre des commentaires !
    Il n'y a jamais rien à quoi il ne faille pas mettre de commentaire.
    (hum... pas très claire cette phrase...)

    Le règle c'est que le commentaire DOIT correspondre au code.
    Mais, au pire, il vaut mieux pas de commentaire du tout plutôt qu'un commentaire qui ne correspond pas.
    Si il n'y a pas de commentaire, le lecteur va chercher à comprendre en lisant le code. C'est pas sympa pour lui, mais il devrait finir pas s'en sortir.
    Si le commentaire ne correspond pas, il va le lire, le croire vrai et ne comprendra plus rien à ce qui suit. Et là c'est vraiment affreux

    Quand on modifie son code, il faut penser à mettre à jour le commentaire.
    C'est un service que l'on rend au lecteur mais aussi à soi-même car on est souvent le lecteur de son propre code.
    Captain'Flam
    anciennement Sopsag, aka Hadrien
    Win seven x64 & Win 10 / Visual 2017 / Python 2.7 / Eclipse

  16. #16
    Expert éminent sénior
    Avatar de Sve@r
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Février 2006
    Messages
    12 685
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Oise (Picardie)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Février 2006
    Messages : 12 685
    Points : 30 974
    Points
    30 974
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par étudiante6 Voir le message
    Sve@r par contre je ne suis pas sûre d'avoir compris pour la convention, pour moi le "t_" était pour tableau, donc quand c'est pour une structure la convention veut qu'on commence par "s_" ?
    Yep. Exemple
    Code c : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    typedef struct s_file {
        char *nom;
        int size;
    } t_file;
    Comme ça, la chaine "file" est disponible pour nommer une variable qui sera du type... t_file
    Code c : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    t_file file1, file2, file3;
    void traitement(t_file *file)

    Pour les tableaux je ne pense pas qu'il y ait de convention particulière mais préfixer un tableau avec "tab_" me parait assez sensé...

    PS: donner un nom propre à la structure (ici "s_file") n'est pas utile ici puisque ce nom n'est jamais réutilisé. C'était juste pour l'exemple...
    Mon Tutoriel sur la programmation «Python»
    Mon Tutoriel sur la programmation «Shell»
    Sinon il y en a pleins d'autres. N'oubliez pas non plus les différentes faq disponibles sur ce site
    Et on poste ses codes entre balises [code] et [/code]

  17. #17
    Futur Membre du Club
    Femme Profil pro
    Formateur en informatique
    Inscrit en
    Décembre 2012
    Messages
    11
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Formateur en informatique

    Informations forums :
    Inscription : Décembre 2012
    Messages : 11
    Points : 6
    Points
    6
    Par défaut
    Merci, pas de soucis pour les commentaires j'essayerai d'en mettre un maximum ! (et qui correspondent au code)

    C'est noté pour les noms de structures merci

    bonne soirée à tous

  18. #18
    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
    Au passage: essayez d'éviter le Franglais quand les mots veulent dirent deux choses différentes selon la langue (ici, "file"): Il vaut mieux mettre tous les champs de la structure en anglais pour éviter la confusion...
    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.

  19. #19
    Futur Membre du Club
    Femme Profil pro
    Formateur en informatique
    Inscrit en
    Décembre 2012
    Messages
    11
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Formateur en informatique

    Informations forums :
    Inscription : Décembre 2012
    Messages : 11
    Points : 6
    Points
    6
    Par défaut
    ça m'étonne de moi donc j'ai vérifié et ce n'est pas moi, regarde ma première version

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    struct file {
      char* name;
      int fd;
      struct t_files* son;
    };
    mais je suis d'accord mélanger anglais et français ce n'est pas très agréable

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

Discussions similaires

  1. Réponses: 5
    Dernier message: 17/01/2008, 13h18
  2. Problème avec les structures et gets!
    Par anis_el_madani dans le forum C
    Réponses: 11
    Dernier message: 23/07/2007, 00h57
  3. Problème avec une structure
    Par titux dans le forum C
    Réponses: 5
    Dernier message: 22/07/2007, 16h26
  4. Problème avec une structure
    Par Pierre.g dans le forum C
    Réponses: 4
    Dernier message: 30/12/2006, 12h22
  5. Probléme avec une structure
    Par astragoth dans le forum C++
    Réponses: 3
    Dernier message: 25/04/2006, 20h31

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