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 :

Créer un arbre binaire complet en C


Sujet :

C

  1. #1
    Nouveau Candidat au Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Novembre 2011
    Messages
    1
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Côte d'Ivoire

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Novembre 2011
    Messages : 1
    Points : 1
    Points
    1
    Par défaut Créer un arbre binaire complet en C
    J'ai un gros problème!
    Je n'arrive pas à créer un arbre binaire complet de telle sorte que tous les noeuds aient exactement deux fils (un fils de droite, un fils de gauche). Voici celui que je propose. Il ne passe que sur l'ordinateur de ma soeur et pas sur le mien (chose que je ne comprends pas non plus).
    Merci de m'aider

    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
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    #include<stdio.h>
    #include<stdlib.h>
    #include<string.h>
     
    //etablissons la structure de notre arbre binaire
     
    typedef struct num
    {
           int valeur;
           struct num *fils_gauche;
           struct num *fils_droit;
           }arbre;
     
    arbre *creerarbre(arbre *A, int x, int n)
    {
          if (A==NULL)
          {
                      A=(arbre*)malloc(sizeof(arbre));//creation de l'arbre
                      A->valeur=x;    //la racine prend une valeur x
                      A->fils_gauche=NULL; //le fils de gauche pointe sur null
                      A->fils_droit=NULL; //le fils de droit pointe sur null
                      n++; //on incrémente le compteur pour atteindre le nombre de niveau souhaité
                      };
          if (n<=7)
          {
                 A->fils_gauche=creerarbre(A->fils_gauche,0,n); //on appelle la fonction pour creer le sous arbre ayant le fils de gauche comme racine
                 A->fils_droit=creerarbre(A->fils_droit,1,n);//on appelle la fonction pour creer le sous arbre ayant le fils de droit comme racine
                   };
          return A;
    }
     
    void parcoursprefixe(arbre *P)
    {
         if(P != 0)
         {
              printf("%d",P->valeur);
              parcoursprefixe(P->fils_gauche);
              parcoursprefixe(P->fils_droit);
              };
    }
     
    int main()
    { 
          arbre *R;
          R=(arbre*)malloc(sizeof(arbre));
          R=creerarbre(R,0,1);
          parcoursprefixe(R);
          getch();
     
    }
    Fichiers attachés Fichiers attachés

  2. #2
    Membre éclairé
    Inscrit en
    Décembre 2010
    Messages
    290
    Détails du profil
    Informations forums :
    Inscription : Décembre 2010
    Messages : 290
    Points : 719
    Points
    719
    Par défaut
    Ton programme est techniquement juste (ou tout du moins je ne vois pas l'erreur). QQ points toutefois :

    - Il est inutile de passer un arbre à la fonction creerarbre(), puisqu'elle se contente d'allouer un noeud et ses descendants.

    - De même, le main peut appeler creerarbre() plutot que d'allouer le noeud racine avec malloc(). Ton code sera plus simple.

    - parcoursprefixe() devrait produire un retour chariot. Parfois, ne pas produire de retour à la ligne empeche le texte de s'afficher (il attend un flush). De tt façons, juste afficher la valeur des noeuds de l'arbre récursivement va te produire un gros bunch de chiffres illisibles.

    Edit : au fait, tu n'as pas dit ce qui ne marchait pas dans ton programme. Quel résultat obtiens tu ?

  3. #3
    Expert éminent sénior
    Avatar de diogene
    Homme Profil pro
    Enseignant Chercheur
    Inscrit en
    Juin 2005
    Messages
    5 761
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Enseignant Chercheur
    Secteur : Enseignement

    Informations forums :
    Inscription : Juin 2005
    Messages : 5 761
    Points : 13 926
    Points
    13 926
    Par défaut
    Ce programme est faux.
    - La ligne n++ est mal placée : elle ne s'exécute que si A == NULL, donc jamais dans le code proposé
    - La condition if(A==NULL)... prévoit que l'arbre sera construit à partir de rien. Il est donc inutile de le construire partiellement dans main()
    - La fonction ne prévoit pas d'échec du malloc(). C'est une grave lacune pour la fiabilité du code.

    Quelques corrections (mais il faut rajouter les tests des malloc()) : Dans ce code, pour vérifier la construction, les valeurs stockées dans les noeux (val1 et val2) sont prévues pour afficher 1,2,3,.... par la fonction parcoursprefixe() à titre de test et devront être changées dans la version définitive.

    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
     
    #define PROF 7
    arbre *creerarbre(arbre *A, int x, int n)
    {
          if (A==NULL)
          {
             A=(arbre*)malloc(sizeof(arbre));//creation de l'arbre
             A->valeur=x;    //la racine prend une valeur x
             A->fils_gauche=NULL; //le fils de gauche pointe sur null
             A->fils_droit=NULL; //le fils de droit pointe sur null
          }
          n++; //on incrémente le compteur pour atteindre le nombre de niveau souhaité
          if (n<PROF)
          {
             int val1 = A->valeur+1;               // pour tester
             int val2 = A->valeur+ pow(2,PROF-n);  // pour tester
             A->fils_gauche=creerarbre(A->fils_gauche,val1,n); //on appelle la fonction pour creer le sous arbre ayant le fils de gauche comme racine
             A->fils_droit=creerarbre(A->fils_droit,val2,n);//on appelle la fonction pour creer le sous arbre ayant le fils de droit comme racine
          }
          return A;
    }
    ...
    int main(void)
    {
          arbre *R;
          R=creerarbre(NULL,1,0);
          parcoursprefixe(R);
          getchar();
          return 0;
    }
    Maintenant, la logique voudrait que le dernier argument de creerarbre() soit la profondeur de l'arbre que l'on veut créer. Le même code dans cette logique devient :
    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
     
    arbre *creerarbre(arbre *A, int x, int prof)
    {
       if (prof>0)
       {
          int val1;   // pour tester
          int val2;   // pour tester
          if (A==NULL)
          {
             A=malloc(sizeof(arbre));//creation de l'arbre
             A->valeur=x;    //la racine prend une valeur x
             A->fils_gauche=NULL; //le fils de gauche pointe sur null
             A->fils_droit=NULL; //le fils de droit pointe sur null
          }
          val1 = A->valeur+1;               // pour tester
          val2 = A->valeur+ pow(2,prof-1);  // pour tester
          A->fils_gauche=creerarbre(A->fils_gauche,val1,prof-1);
          A->fils_droit=creerarbre(A->fils_droit,val2,prof-1);
       }
       return A;
    }
    ....
    int main(void)
    {
          arbre *R;
          R=creerarbre(NULL,1,7);
          parcoursprefixe(R);
          getchar();
          return 0;
    }
    Publication : Concepts en C

    Mon avatar : Glenn Gould

    --------------------------------------------------------------------------
    Une réponse vous a été utile ? Remerciez son auteur en cliquant le pouce vert !

  4. #4
    Candidat au Club
    Femme Profil pro
    Administrateur de base de données
    Inscrit en
    Décembre 2017
    Messages
    3
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Âge : 25
    Localisation : Algérie

    Informations professionnelles :
    Activité : Administrateur de base de données

    Informations forums :
    Inscription : Décembre 2017
    Messages : 3
    Points : 3
    Points
    3
    Par défaut
    mais j comprend pas prk vous avez pas cree la racine d abord j arrive pas a l faire si qlq peut m aider svp et merci

  5. #5
    Expert éminent
    Homme Profil pro
    Ingénieur développement matériel électronique
    Inscrit en
    Décembre 2015
    Messages
    1 565
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 61
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Ingénieur développement matériel électronique
    Secteur : High Tech - Électronique et micro-électronique

    Informations forums :
    Inscription : Décembre 2015
    Messages : 1 565
    Points : 7 648
    Points
    7 648
    Par défaut
    Bonjour,

    Une règle incontournable du C est qu'une fonction ne peut pas modifier un paramètre passé, le seul moyen est de passer l'adresse d'une donnée et la fonction utilisera ce pointeur pour y mettre quelque chose.

    La fonction creerarbre() si elle reçoit un arbre *A, ne pourra utiliser ce A que pour y remplir (ou lire) les 3 champs de l'arbre. Elle ne pourra pas changer le pointeur qu'elle reçoit, elle n'agira que sur ce qui est pointé.
    Si on vient de créer un arbre pointé par A, en appelant creerarbre( A->fils_gauche , ..... ), la fonction recevra sa valeur donc NULL, et ne pourra la changer. Donc finalement ce paramètre est toujours NULL dans ton cas comme l'a déjà dit diogene et donc ne sert à rien.
    Ici ta fonction reçoit un arbre* et retourne un arbre*, ces 2 possibilités ne font que complexifier la solution. Il faudrait ou bien que la fonction modifie son paramètre ou bien qu'elle fabrique un arbre et retourne un pointeur dessus. Ce qui donne soit void creerarbre(arbre **ptptA , .....) soit arbre* creerarbre( .....). Le premier cas nécessite un pointeur de pointeur qui est un peu lourd pour un débutant, intéressons nous au second.

    Le second paramètre x est la valeur à affecter à valeur, ce qui n'a pas beaucoup de sens car plusieurs seront créés, on pourrait faire que cette valeur évolue pour mieux reconnaître les nœuds.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    arbre* creerarbre( int valRacine , int niv ) {
       if ( niv < 0 )
          return NULL;
       arbre*  a = malloc( sizeof *a );
       a->valeur = valRacine;
       int delta = 1 << niv; // les fils gauches et droites auront une valeur dépendant de la profondeur 
       a->fils_gauche = creerarbre( valRacine - delta , niv - 1 );
       a->fils_droite = creerarbre( valRacine + delta , niv - 1);
       return a;
    }

  6. #6
    Expert confirmé
    Inscrit en
    Mars 2005
    Messages
    1 431
    Détails du profil
    Informations forums :
    Inscription : Mars 2005
    Messages : 1 431
    Points : 4 182
    Points
    4 182
    Par défaut
    Et donc, tu comptes développer ? Dans les deux sens du terme..

    Après avoir profané le repos éternel de ce fil, tu réponds « j'ai rien pigé » à un exemple complet accompagné d'une quinzaine de lignes explicatives.. T'as pas le sentiment de manquer de respect à ton interlocuteur ? Au bout d'un moment, faut penser à se prendre en main.

  7. #7
    Modérateur
    Avatar de dinobogan
    Homme Profil pro
    ingénieur
    Inscrit en
    Juin 2007
    Messages
    4 073
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France

    Informations professionnelles :
    Activité : ingénieur
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 4 073
    Points : 7 163
    Points
    7 163
    Par défaut
    Elle ne fonctionne pas, qu'est-ce que cela signifie ? Le compilateur sort des erreurs ? Le programme s'exécute mais plante ? Ou ne sort pas le résultat attendu ?
    N'oubliez pas de consulter les FAQ Java et les cours et tutoriels Java
    Que la force de la puissance soit avec le courage de ta sagesse.

  8. #8
    Candidat au Club
    Femme Profil pro
    Administrateur de base de données
    Inscrit en
    Décembre 2017
    Messages
    3
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Âge : 25
    Localisation : Algérie

    Informations professionnelles :
    Activité : Administrateur de base de données

    Informations forums :
    Inscription : Décembre 2017
    Messages : 3
    Points : 3
    Points
    3
    Par défaut
    oui ne sort pas de resultat il m affiche erreure j pense que avec void ca marche pas j ai pas compris

  9. #9
    Candidat au Club
    Femme Profil pro
    Administrateur de base de données
    Inscrit en
    Décembre 2017
    Messages
    3
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Âge : 25
    Localisation : Algérie

    Informations professionnelles :
    Activité : Administrateur de base de données

    Informations forums :
    Inscription : Décembre 2017
    Messages : 3
    Points : 3
    Points
    3
    Par défaut
    svp vous pouvez m aider a trie un arbre binaire non ordonne en c j arrive pas a le faire et merci

Discussions similaires

  1. Arbre binaire localement complet
    Par abysr dans le forum Algorithmes et structures de données
    Réponses: 1
    Dernier message: 04/05/2015, 11h19
  2. Créer un arbre binaire et l'afficher
    Par hellowo dans le forum Débuter
    Réponses: 9
    Dernier message: 19/03/2015, 21h38
  3. Afficher un arbre binaire avec sa structure
    Par PhoneKilleR dans le forum C
    Réponses: 7
    Dernier message: 23/04/2008, 23h24
  4. Arbre binaire
    Par Heaven dans le forum Algorithmes et structures de données
    Réponses: 6
    Dernier message: 02/02/2004, 19h01
  5. [LG]probleme de creation arbre binaire
    Par jsaviola dans le forum Langage
    Réponses: 2
    Dernier message: 06/01/2004, 20h57

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