Partage
  • Partager sur Facebook
  • Partager sur Twitter

Structure en C

Sujet résolu
    19 avril 2023 à 11:59:50

    Bonjour à tous, 

    J'aimerai créer un programme qui lit une suite d'adresses dans un fichier et les met dans une structure et affichez les différentes parties de la structure comme ceci : 

    Voici mon code mais quand je le compile rien ne se passe :(

    #include <stdio.h>
    #include <stdlib.h>
    
    
    struct adresse
    {
        int numero ;
        char voie [10];
        char nomVoie [255];
        char ville [40] ;
        int codePostal ;
    
    } ;
    
    /* Fonction qui va nous permettre de lire notre fichier*/
    int main() {
    
        FILEfile = fopen("adresse.txt", "r");
        if (file == NULL) {
            printf("Ce fichier n'a pu etre ouvert. \n ");
            return 1;
        }
    
        /* créer notre tableau de données à partir de notre structure*/
    
        struct adresse tableau_adresse[20];
    
        /* Lire les éléments depuis le fichier texte et les mettre dans le tableau*/
        int i = 0;
        while (fscanf(file, "%d %s %s %s %d", &tableau_adresse[i].numero, tableau_adresse[i].voie, tableau_adresse[i].nomVoie, tableau_adresse[i].ville, &tableau_adresse[i].codePostal) != EOF) {
            i++;
        }
    
        /*Afficher les éléments */
    
        for (int j = 0; j < i; j++) {
            printf("Addresse : %d\n", j+1);
            printf("Numéro : %d\n", tableau_adresse[j].numero);
            printf("Voie: %s\n", tableau_adresse[j].voie);
            printf("Nom de voie : %s\n", tableau_adresse[j].nomVoie);
            printf("Ville: %s\n", tableau_adresse[j].ville);
            printf("Code Postal: %d\n", tableau_adresse[j].codePostal);
        }
    
        /* Fermer le fichier */
        fclose(file);
    
        return 0;
    }
    


    Je vous remercie pour votre aide !

    • Partager sur Facebook
    • Partager sur Twitter
      19 avril 2023 à 12:15:41

      Ton code ne compile pas à cause de la ligne 12 !?

      En corrigeant ça compile et fonctionne (à condition que le fichier adresse.txt soit bien formé et qu'il n'y ai pas d'espace dans les chaines de caractères Voie, NomVoie et Ville). 

      -
      Edité par rouIoude 19 avril 2023 à 12:18:06

      • Partager sur Facebook
      • Partager sur Twitter
      ...
        19 avril 2023 à 13:37:17

        Hello, 

        Merci pour ta réponse. J'ai supprimé la ligne 12 mais ça ne fonctionne toujours pas.

        J'avais aussi corrigé la ligne 18 FILE  * file = open...

        Voilà comment se présente mon fichier adresse.txt :

        5

        Rue

        De la paix

        Paris 

        75000

        -
        Edité par Fat. C. 19 avril 2023 à 13:42:16

        • Partager sur Facebook
        • Partager sur Twitter
          19 avril 2023 à 13:55:43

          Je voulais bien dire ligne 18 (erreur de ma part).

          Ça fonctionne pas à cause du nom de la rue qui est en trois mots.

          rouIoude a écrit:

          et qu'il n'y ai pas d'espace dans les chaines de caractères Voie, NomVoie et Ville. 

          Les fscanf avec %s lisent jusqu'au prochain caractère blanc dont l'espace fait parti.

          Comme tu as une donnée par ligne tu peux lire jusqu'au '\n' :

          while (fscanf(file, "%d %9[^\n] %254[^\n] %39[^\n] %d", ...

          A savoir que scanf retourne le nombre de donnée corectement lue (ici 5), tu peut donc tester son retour pour savoir si tout c'est bien passé. 

          • Partager sur Facebook
          • Partager sur Twitter
          ...
            19 avril 2023 à 14:03:07

            du coup comment je peux faire pour avoir le nom de la rue en entier avec les espaces ? Je sais que je devrais mettre un truc du genre %[^\n] mais dans mon  cas je ne sais pas comment l'appliquer pour qu'il lise bien l'élément suivant le code postal...

            -
            Edité par Fat. C. 19 avril 2023 à 14:09:26

            • Partager sur Facebook
            • Partager sur Twitter
              19 avril 2023 à 14:13:27

              code postal tu l'as mis en int alors c'est %d

              Tu n'as pas lu mon post en entier ? notament le bout de code.

              • Partager sur Facebook
              • Partager sur Twitter
              ...
                19 avril 2023 à 16:08:04

                Oui désolée j'ai lu trop vite ! 

                ça fonctionne mille mercis pour ton aide précieuse :)

                Très belle journée !

                • Partager sur Facebook
                • Partager sur Twitter
                  12 juillet 2023 à 15:16:48

                  Bonjour à tous !! Voilà ma bouteille à la mer! ^^

                  J'essaie depuis 4 jours d'écrire un répertoire en langage C, semblable à ceux des téléphones, afin d'exercer la manipulation de struct avec des pointeurs et notamment des tableaux de pointeurs. J'ai condensé le code pour qu'il ne vous soit pas trop pénible...

                  Si quelqu'un pourrait m'expliquer aussi les warning je lui en serai énormément reconnaissant!

                  PS : Le programme compile, s'affiche mais ne tourne pas du tout...

                  PROGRAMME

                  C:\programmation\formation vidéo\Entrainement\Entrainement libre\révisions\09____structure\01\repertoire0X>a.exe
                  
                  C:\programmation\formation vidéo\Entrainement\Entrainement libre\révisions\09____structure\01\repertoire0X>
                  



                  COMPILATION

                  C:\programmation\formation vidéo\Entrainement\Entrainement libre\révisions\09____structure\01\repertoire0X>gcc *.c
                  charnet.c: In function 'initialiser_repertoire':
                  charnet.c:14:57: warning: assignment to 'signed char' from 'char *' makes integer from pointer without a cast [-Wint-conversion]
                     14 |                         *PRcarnet[i]->prenom            = "prenom               : vide";
                        |                                                         ^
                  charnet.c:15:65: warning: assignment to 'signed char' from 'char *' makes integer from pointer without a cast [-Wint-conversion]
                     15 |                         *PRcarnet[i]->nom                       = "nom                  : vide";
                        |                                                                 ^
                  charnet.c:16:57: warning: assignment to 'signed char' from 'char *' makes integer from pointer without a cast [-Wint-conversion]
                     16 |                         *PRcarnet[i]->telephonne        = "telephonne   : vide";
                        |                                                         ^
                  charnet.c:17:65: warning: assignment to 'signed char' from 'char *' makes integer from pointer without a cast [-Wint-conversion]
                     17 |                         *PRcarnet[i]->email                     = "email                : vide";
                        |                                                                 ^
                  charnet.c:18:57: warning: assignment to 'signed char' from 'char *' makes integer from pointer without a cast [-Wint-conversion]
                     18 |                         *PRcarnet[i]->adresse           = "adresse              : vide";
                        |                                                         ^
                  charnet.c:19:57: warning: assignment to 'signed char' from 'char *' makes integer from pointer without a cast [-Wint-conversion]
                     19 |                         *PRcarnet[i]->localite          = "localite     : vide";
                        |                                                         ^
                  main.c: In function 'main':
                  main.c:14:41: warning: passing argument 2 of 'initialiser_repertoire' from incompatible pointer type [-Wincompatible-pointer-types]
                     14 |         initialiser_repertoire (carnet, *PRcarnet);
                        |                                         ^~~~~~~~~
                        |                                         |
                        |                                         Contact *
                  In file included from main.c:4:
                  charnet.h:18:58: note: expected 'Contact **' but argument is of type 'Contact *'
                     18 | void initialiser_repertoire (Contact carnet[], Contact *(PRcarnet[]));
                        |                                                ~~~~~~~~~~^~~~~~~~~~~
                  



                  "CHARNET.C"

                  #include <stdio.h>
                  #include <stdlib.h>
                  #include <string.h>
                  #include "charnet.h"
                  
                  void initialiser_repertoire (Contact carnet[], Contact *(PRcarnet[]))
                  {
                  		//connexion entre pointeurs et variables + initialisation
                  		for (int i = 0; i<15; i++)
                  		{
                  			PRcarnet[i] = &(carnet[i]); //connexions
                  	
                  			*PRcarnet[i]->ordre			= i++; //initialisation
                  			*PRcarnet[i]->prenom	 	= "prenom 		: vide";
                  			*PRcarnet[i]->nom 			= "nom 			: vide";
                  			*PRcarnet[i]->telephonne 	= "telephonne 	: vide";
                  			*PRcarnet[i]->email			= "email 		: vide";
                  			*PRcarnet[i]->adresse		= "adresse 		: vide";
                  			*PRcarnet[i]->localite		= "localite 	: vide";
                  		}
                  };
                  



                  CHARNET.H

                  #ifndef		charnet_h
                  #define		charnet_h
                  #define TAILLE_MAX	50
                  
                  typedef struct Contact Contact;			// Déclaration struct, variable personnalisée
                  struct Contact
                  {
                  signed char ordre		[TAILLE_MAX];
                  signed char prenom 		[TAILLE_MAX];
                  signed char nom 		[TAILLE_MAX];
                  signed char telephonne	        [TAILLE_MAX];
                  signed char email		[TAILLE_MAX];
                  signed char adresse		[TAILLE_MAX];
                  signed char localite	        [TAILLE_MAX];
                  };
                  /*__________________________________________________________________________________________________________________*/
                  
                  void initialiser_repertoire (Contact carnet[], Contact *(PRcarnet[]));
                  
                  
                  
                  #endif

                  MAIN.C

                  #include <stdio.h>
                  #include <stdlib.h>
                  #include <string.h>
                  #include "charnet.h"
                  
                  #define TAILLE_MAX	50
                  #define NBRE_CONTACT 15
                  
                  int main ()
                  {
                  Contact carnet 		[NBRE_CONTACT];				//Déclaration variable << carnet >>
                  Contact *PRcarnet	[NBRE_CONTACT];				//Déclaration pointeurs pour sous-variable de << carnet >>
                  
                  initialiser_repertoire (carnet, *PRcarnet);		//connexions pointeur->sous-variables // initialisations sous-variables
                  
                  printf ("%s\n%s\t%s\n%s\t%s\n%s\t%s", carnet[4].ordre, carnet[2].prenom, carnet[6].nom, carnet[1].telephonne, carnet[0].email, carnet[3].adresse, carnet[9].localite);
                  
                  system ("pause");
                  return 0;
                  }

                  -
                  Edité par Boozart 12 juillet 2023 à 15:28:32

                  • Partager sur Facebook
                  • Partager sur Twitter
                    12 juillet 2023 à 16:26:41

                    DanielCustodio a écrit:

                    Bonjour à tous !! Voilà ma bouteille à la mer! ^^

                    Il ne faut pas prendre une bouteille qui contient déjà des messages. 

                    Alors la bonne méthode est de créer un nouveau sujet pour y poser ta question !



                    • Partager sur Facebook
                    • Partager sur Twitter
                    ...
                      12 juillet 2023 à 16:26:55

                      DanielCustodio a écrit:

                      Bonjour à tous !! Voilà ma bouteille à la mer! ^^

                      J'essaie depuis 4 jours d'écrire un répertoire en langage C, semblable à ceux des téléphones, afin d'exercer la manipulation de struct avec des pointeurs et notamment des tableaux de pointeurs. J'ai condensé le code pour qu'il ne vous soit pas trop pénible...

                      Si quelqu'un pourrait m'expliquer aussi les warning je lui en serai énormément reconnaissant!

                      PS : Le programme compile, s'affiche mais ne tourne pas du tout...

                      Bonjour

                      • tu aurais dû faire ton propre sujet au lieu de squatter un truc existant
                      • les warnings sont à 99% révélateurs de problèmes de fond, qui feront planter le programme.  Ils correspondent à des avertissements sur des choses que le langage C, qui est mal foutu, considère comme légales, mais ne font généralement pas ce qu'on veut.
                      • donc avec des messages d'avertissement, on peut pas vraiment dire que la compilation est un succès.
                      Il suffit de bien lire les messages, calmement. Prenons le premier
                      warning: assignment to 'signed char' from 'char *' makes integer from pointer without a cast [-Wint-conversion]
                         14 |                         *PRcarnet[i]->prenom            = "prenom               : vide";
                            |                                                         ^
                      c

                      Ca dit que tu essaies d'affecter (assignment) un pointeur (char *) dans un entier signé (signed char, en C, les caractères sont des entiers.

                      • Le pointeur, c'est la partie droite de l'affectation, la chaine littérale "prenom" (une chaine c'est un tableau de caractères, assimilé à un pointeur de caractères dans ce contexte.
                      • Le "signed char", c'est donc 
                        *PRcarnet[i]->prenom

                      Pourquoi  le compilateur dit il ça ? Parce que c'est ce que tu as écrit dans ton code. Pourquoi c'est-ce un signed char ?

                      • PRcarnet[i] est un pointeur sur un  Contact (voir définition du paramètre de la fonction)
                      • PRcarnet[i]->prenom est donc le champ (membre) prenom d'une structure Contact
                      • il est de type "tableau de signed char"
                      • Dans ce contexte (précédé par une *), il est assimilé à un pointeur de signed char.
                      • *PRcarnet[i]->prenom  déréférence ce pointeur, et donne accès au premier élément du tableau, c'est comme si tu avait écrit  PRcarnet[i]->prenom[0]
                      • et c'est de type signed char.

                      Donc voila l'explication détaillée de l'erreur.

                      Pourquoi tu as fait cette erreur ?  Parce que comme tous les débutants en C, tu te perds dans les pointeurs (c'est délicat / un peu merdique) et  tu tentes de t'en sortir en mettant des & et des * au hasard, qui sait sur un malentendu ça pourrait marcher.

                      Ce qu'il faudrait faire à la place ? Reprendre calmement.  Et se souvenir que pour copier une chaîne dans une autre, il faut mettre un coup de strcpy.

                      PS pour l'ordre, le compilateur ne proteste pas parce que c'est légal du point de vue de la norme du langage, ça affecte un entier (la valeur de i++) dans le premier caractère du champ ordre. Un entier dans un caractère qui est un petit entier, pourquoi pas, on a le droit. Mais c'est probablement pas ce que tu souhaites faire.

                      -
                      Edité par michelbillaud 12 juillet 2023 à 16:35:07

                      • Partager sur Facebook
                      • Partager sur Twitter
                        12 juillet 2023 à 17:29:59

                        michelbillaud a écrit:

                        DanielCustodio a écrit:

                        Bonjour à tous !! Voilà ma bouteille à la mer! ^^

                        J'essaie depuis 4 jours d'écrire un répertoire en langage C, semblable à ceux des téléphones, afin d'exercer la manipulation de struct avec des pointeurs et notamment des tableaux de pointeurs. J'ai condensé le code pour qu'il ne vous soit pas trop pénible...

                        Si quelqu'un pourrait m'expliquer aussi les warning je lui en serai énormément reconnaissant!

                        PS : Le programme compile, s'affiche mais ne tourne pas du tout...

                        Bonjour

                        • tu aurais dû faire ton propre sujet au lieu de squatter un truc existant
                        • les warnings sont à 99% révélateurs de problèmes de fond, qui feront planter le programme.  Ils correspondent à des avertissements sur des choses que le langage C, qui est mal foutu, considère comme légales, mais ne font généralement pas ce qu'on veut.
                        • donc avec des messages d'avertissement, on peut pas vraiment dire que la compilation est un succès.
                        Il suffit de bien lire les messages, calmement. Prenons le premier
                        warning: assignment to 'signed char' from 'char *' makes integer from pointer without a cast [-Wint-conversion]
                           14 |                         *PRcarnet[i]->prenom            = "prenom               : vide";
                              |                                                         ^
                        c

                        Ca dit que tu essaies d'affecter (assignment) un pointeur (char *) dans un entier signé (signed char, en C, les caractères sont des entiers.

                        • Le pointeur, c'est la partie droite de l'affectation, la chaine littérale "prenom" (une chaine c'est un tableau de caractères, assimilé à un pointeur de caractères dans ce contexte.
                        • Le "signed char", c'est donc 
                          *PRcarnet[i]->prenom

                        Pourquoi  le compilateur dit il ça ? Parce que c'est ce que tu as écrit dans ton code. Pourquoi c'est-ce un signed char ?

                        • PRcarnet[i] est un pointeur sur un  Contact (voir définition du paramètre de la fonction)
                        • PRcarnet[i]->prenom est donc le champ (membre) prenom d'une structure Contact
                        • il est de type "tableau de signed char"
                        • Dans ce contexte (précédé par une *), il est assimilé à un pointeur de signed char.
                        • *PRcarnet[i]->prenom  déréférence ce pointeur, et donne accès au premier élément du tableau, c'est comme si tu avait écrit  PRcarnet[i]->prenom[0]
                        • et c'est de type signed char.

                        Donc voila l'explication détaillée de l'erreur.

                        Pourquoi tu as fait cette erreur ?  Parce que comme tous les débutants en C, tu te perds dans les pointeurs (c'est délicat / un peu merdique) et  tu tentes de t'en sortir en mettant des & et des * au hasard, qui sait sur un malentendu ça pourrait marcher.

                        Ce qu'il faudrait faire à la place ? Reprendre calmement.  Et se souvenir que pour copier une chaîne dans une autre, il faut mettre un coup de strcpy.

                        PS pour l'ordre, le compilateur ne proteste pas parce que c'est légal du point de vue de la norme du langage, ça affecte un entier (la valeur de i++) dans le premier caractère du champ ordre. Un entier dans un caractère qui est un petit entier, pourquoi pas, on a le droit. Mais c'est probablement pas ce que tu souhaites faire.

                        -
                        Edité par michelbillaud il y a environ 1 heure

                        Je n'avais pas compris le protocole... Je m'excuse  de squatté une autre bouteille !! MERCI D'Y AVOIR REPONDU!!!!!

                        D'accord. Je vais retravailler les pointeurs. j'essaie déjà de bien assimiler ces explications en retravaillant sur le code et je reviens vers vous!

                        ça fait trop plaisir d'avoir quelqu'un pour nous aider!!! MERCI!

                        PS : Je fait un nouveau sujet ou on continue ici ????



                        -
                        Edité par Boozart 12 juillet 2023 à 17:31:02

                        • Partager sur Facebook
                        • Partager sur Twitter
                          12 juillet 2023 à 18:21:06

                          Boozart a écrit:

                          PS : Je fait un nouveau sujet ou on continue ici ????

                          Fait un nouveau sujet, on partira sur de bonnes bases.

                          • Partager sur Facebook
                          • Partager sur Twitter
                          ...
                            12 juillet 2023 à 20:18:02

                            Boozart a écrit:


                            PS : Je fait un nouveau sujet ou on continue ici ????

                            Si le problème est réglé,  ça sera des questions sur autre chose => un autre sujet
                            • Partager sur Facebook
                            • Partager sur Twitter

                            Structure en C

                            × 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