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 :

Passage d'un parametre problematique


Sujet :

C

  1. #1
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    6
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 6
    Par défaut Passage d'un parametre problematique
    Bonsoir,

    J'ai un probleme dans le (mon) code suivant avec la fonction
    void affiche_caracteristiques(char *name,int *code) qui prends en paramètre dans le main deux champs (name et codePostal) de la structure user1 (de type personne).


    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
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
     struct personne {
     
    char  *name;
    int codePostal;
     
     
    };
     
    int SaisieCode(void);   // demande de saisir un code postal
     
    int format_alphabetique(char *nom);   // utilisée par la fonction SaisieNom ci-dessous
     
    char * SaisieNom (void)       //demande de saisir un nom
    {
      char Nom[41];     
      do
      {
           printf("Entrez le nom\n");
           fgets(Nom, sizeof Nom, stdin);             // Lire Nom au clavier
           if(!(format_alphabetique(Nom)))            // Emettre un message d'erreur ?
           {
               printf("Merci d'utiliser des lettres Majuscules ou minuscules\n");
           }
      }
     
      while (!(format_alphabetique(Nom)));    // Tant que le Nom n'est pas de format alphabetique
     
     return Nom;
     
    }
     
     
     
    void affiche_caracteristiques(char *name,int *code)   // NE FONCTIONNE PAS
    {
     
      printf("Le nom est: %c\n",name);                    // cette ligne ne fonctionne pas : 8 est affiché quelque soit la chaine que je veux passer en parametre
      printf("Votre code postal est le :%i",*code);       // Cette ligne fonctionne correctement et affiche bien la valeur du code postal
    }
     
     
     
     
    int main()  
    {
        char fin=0;
        char choix;
        struct personne user1;      // Création d'un objet personne de nom user1
        user1.name = "NON SAISI";   // Initialisation des données de la personne user1
        user1.codePostal = -1;      // conformément au cahier des charges
     
        // AFFICHAGE DU MENU :
    while(!fin)                    // Tant que fin est faux, le programme boucle sur le menu principal :
    {
        printf("\n\n");
        printf("1.Saisie du nom\n2.Saisie du code postal\n3.Affichage des caracteristiques de la personne\n4.Fin \n");
        choix = getchar();
        fflush(stdin);
     
    switch (choix)                // Aiguillage en fonction du choix
     {
     
    case '1' :
     
      user1.name = SaisieNom();   // Appel pour saisir le premier champs (le nom)
     
        printf("La 3eme lettre de ton nom est: %c\n",user1.name[2]);  // Debug
    	break;
     
    case '2' :
     
    	user1.codePostal = SaisieCode();    // Appel pour saisir le code postal 
     
    	break;
     
    case '3' :
     
    	affiche_caracteristiques(&user1.name,&user1.codePostal);    // Je passe en parametre les adresses des champs de ma srtucture user1 à la fonction d'affichage
    	break;
     
    default:  fin=1;     // Si on choisit 4 on met fin à 1 (true) ce qui provoque la sortie de la boucle while et le retour du programme
     
        break;
     
      }
     
    }
    return 0;
    }
    Je veux afficher à l'écran name et codePostal. Ce qui ne fonctionne pas du tout pour name. Avez-vous une idée d'où ça peut bloquer ? (définition de la structure ? parametre d'afficher_caractéristiques ? dans le printf ? ...)

    Guillaume

    ps : Je n'ai pas fait apparaitre certaines fonctions, en mettant simplement leurs définitions

  2. #2
    Expert confirmé
    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
    Par défaut
    Bonjour et bienvenue sur le forum

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    char * SaisieNom (void)       //demande de saisir un nom
    {
      char Nom[41];     
    ....
     
     return Nom;
     
    }
    Tu retournes l'adresse d'une variable locale ( Dans return Nom, Nom est l'adresse du premier élément du tableau). Or les variables locales sont détruites en sortie de fonction et on a alors l'adresse d'une variable qui n'existe plus.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    void affiche_caracteristiques(char *name,int *code)   // NE FONCTIONNE PAS
    {
     
      printf("Le nom est: %c\n",name);                    // cette ligne ne fonctionne pas : 8 est affiché quelque soit la chaine que je veux passer en parametre
      printf("Votre code postal est le :%i",*code);       // Cette ligne fonctionne correctement et affiche bien la valeur du code postal
    }
    Le format %c est pour l'affichage d'un char, pas d'une chaîne de char. Le format devrait être %s

    a un comportement indéfini : sur certaines plateformes, ça ne fonctionne pas. fflush() ne devrait être utilisé que sur des flux de sortie (comme stdout)

  3. #3
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    6
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 6
    Par défaut
    Bonsoir diogene et merci pour ton acceuil

    Merci pour l'explication je comprends ce qui se passe maintenant.

    Je fais essayer de solutionner ça en passant en paramètre le champs de la structure que je veux modifier, dans la fonction :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    SaisieNom(&user1.name);
    C'est comme cela que l'on fait en C, apparemment.


    Cependant, une chose étrange est que ce morceau fonctionne :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    user1.name = SaisieNom();   // Appel pour saisir le premier champs (le nom)
     
        printf("La 3eme lettre de ton nom est: %c\n",user1.name[2]);
    => le printf m'affiche bien la 3eme lettre du nom que je saisie. La fonction SaisieNom() fonctionne donc.

    Bref, je modifie mon code et je reposte une fois les tests effectués. Le C est vraiment déroutant pour moi qui vient de java !

  4. #4
    Expert confirmé
    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
    Par défaut
    Cependant, une chose étrange est que ce morceau fonctionne :
    C'est uniquement un hasard : la mémoire n'a pas encore été récupérée pour y mettre autre chose. C'est d'ailleurs une malchance, parce que au lieu de planter là où il y a l'erreur, ça va planter plus tard ailleurs.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    SaisieNom(&user1.name);
    Là aussi, ça va planter si tu ne fais pas attention : le champ name est un pointeur et toi, il te faut un tableau pour placer tes caractères.
    Donc :
    - Soit tu gardes name comme un pointeur et tu dois faire de l'allocation dynamique dans ta fonction pour allouer de quoi stocker la chaîne et placer l'adresse dans name,
    - Soit tu changes name pour un tableau de caractères (assez grand pour les mettre tous + le zéro terminal). Dans ce cas & ne doit pas figurer dans l'appel

  5. #5
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    6
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 6
    Par défaut
    Arf, malgré ton aide, je n'y arrive pas !

    J'ai réussi à afficher "Gu" mais Guillaume ne veut pas sortir. J'ai adopté la stratégie tableau name sur ton conseil, et ne me sentant pas du tout à l'aise avec les malloc...

    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
    struct personne {
     
    char name[41];
    int codePostal;
     
    };
     
    void SaisieNom (char Nom[41]){
    fgets(Nom, sizeof Nom, stdin);
    }
     
    void affiche_caracteristiques(char name[41],int *code)   
    {
         // Je ne vois pas quoi mettre ici
    }
    J'ai essayé d'afficher avec un unique printf("%s",name); ou de balayer sur chaque caractère de name jusqu'à rencontrer \0, mais je n'accede pas correctement aux caractère... Peux-tu me donner les 2 syntaxes à utiliser ?

    Main :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
     
    int main(){
     
    struct personne user1;           // Création d'un objet personne de nom user1
     
    SaisieNom(user1.name);   
    fflush(stdin);
     
    affiche_caracteristiques(user1.name,59000);
    return 0;
    }
    En tappant SaisieNom(user1.name) comme tu le suggère, user1.name ne sera pas modifié par la fonction, mais juste recopié localement, non ?

    Donc je ne vois pas comment ca marche. J'ai peut être mal interprété ta proposition.

  6. #6
    Expert confirmé
    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
    Par défaut
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    En tappant SaisieNom(user1.name) comme tu le suggère, user1.name ne sera pas modifié par la fonction, mais juste recopié localement, non ?
    Oui, comme pour tout tranfert de paramètres.
    MAIS, user1.name désigne un tableau donc c'est l'adresse du premier élément qui est passé. Si la fonction connait l'adresse du premier élément et la taille d'un élément (donné par le type de user1.name) elle peut accéder à tous les éléments du tableau (ce qu'elle ne connait pas à priori, c'est le nombre d'éléments du tableau).
    Donc si la fonction écrit à l'adresse user1.name, on écrit dans le tableau et SaisieNom(user1.name) permet de charger le tableau.

    Par contre, il y a un problème ici :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    void SaisieNom (char Nom[41]){
    fgets(Nom, sizeof Nom, stdin);
    }
    Dans le paramètre char Nom[41] , le 41 ne sert à rien et est ignoré par le compilateur. C'est équivalent à écrire
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    void SaisieNom (char Nom[]){
    et ceci est interprété par le compilateur (dans une liste de paramètres) comme
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    void SaisieNom (char *Nom){
    Cette dernière forme montre qu'en fait Nom est un pointeur et lorsque tu écris sizeof Nom tu obtiens la taille d'un pointeur (probablement 4), pas la taille du tableau ! Comme je te le disais plus haut, la fonction ne connait pas le nombre d'éléments du tableau. Si elle en a besoin, il faut le lui passer en paramètre :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    void SaisieNom (char Nom[], size_t dim){
    fgets(Nom, dim , stdin);
    }
    int main(){
    struct personne user1;           // Création d'un objet personne de nom user1 
    SaisieNom(user1.name, 41);   
    affiche_caracteristiques(user1.name,59000);
    return 0;
    }
    Dans la fonction affiche_caracteristiques(), pourquoi le paramètre code est-il un pointeur sur int et pas un int ?
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    void affiche_caracteristiques(char name[], int code)   
    {
         printf( "nom =%s ; code = %d \n",name,code);
    }

  7. #7
    Membre émérite
    Avatar de Pouet_forever
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    671
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 671
    Par défaut
    On n'utilise jamais fflush sur stdin !
    La norme ne précise l'utilisation de fflush que sur un flux sortant, mais sur stdin ... tout peut arriver

  8. #8
    Inactif  
    Avatar de Mac LAK
    Profil pro
    Inscrit en
    Octobre 2004
    Messages
    3 893
    Détails du profil
    Informations personnelles :
    Âge : 51
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations forums :
    Inscription : Octobre 2004
    Messages : 3 893
    Par défaut
    Citation Envoyé par Pouet_forever Voir le message
    On n'utilise jamais fflush sur stdin !
    La norme ne précise l'utilisation de fflush que sur un flux sortant, mais sur stdin ... tout peut arriver
    Cela dépend de la cible... Et de son niveau de respect de la norme, et surtout, de la norme en question.
    Suivant la plate-forme de développement, cela peut être la manière la plus rapide et la plus efficace pour purger le buffer d'entrée.
    Mac LAK.
    ___________________________________________________
    Ne prenez pas la vie trop au sérieux, de toutes façons, vous n'en sortirez pas vivant.

    Sources et composants Delphi sur mon site, L'antre du Lak.
    Pas de question technique par MP : posez-la dans un nouveau sujet, sur le forum adéquat.

    Rejoignez-nous sur : Serveur de fichiers [NAS] Le Tableau de bord projets Le groupe de travail ICMO

  9. #9
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    6
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 6
    Par défaut
    Mac et Pouet : Utilisation de fflush(stdin);

    fflush(); en fait bondir plus d'un ! Alors, qu'utiliser ? Un balayage sur stdin avec getchar() est elle la bonne méthode ?

    Je programme sous CodeBlocks dans Windows. Cible, norme, respect du niveau de la cible... ces termes sont plutot abscons pour moi.

    Diogene :

    Merci Diogene , mon problème est résolu, et je saisis un peu mieux les nuances sur les tableaux. Je vais prendre pour réflexe la communication de la taille du tableau avec size_t dim. Je ne connaissais pas !

    Dans la fonction affiche_caracteristiques(), pourquoi le paramètre code est-il un pointeur sur int et pas un int ?
    Mes profs nous encouragent à passer des pointeurs en paramètre des fonctions, plutot que de copier les variables localement aux fonctions (sans pointeur). Je pensais que c'était une bonne habitude à prendre.

    Dans un autre programme, je passe des pointeurs vers des structures en paramètre :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    int ModifierStruct (struct femme *carmen, int tourDePoitrine){
     
    (*carmen).tour= tourDePoitrine;
     
    }
    J'ai lu que c'était une bonne méthode, si par exemple ma structure contenait 1000 champs ; ils ne sont pas recopiés dans la fonction appelée.

    Je code avec CodeBlocks. Hé bien j'ai pas mal galéré avant de me rendre compte par exemple qu'il faut bien ecrire (*carmen).tour= tourDePoitrine; sans oublier les parenthèses... ! J'imagine que c'est interprété différemment d'un compilateur à l'autre.

    Un dernier point :

    Je souhaite initialiser user1.name à "NON SAISI\0"

    Mon cours semble dire que les commandes suivantes le permettent :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    user1.name = {'N','O','N',' ','S','A','I','S','I','\0'};
    //ou
    user1.name = "NON SAISI\0";
    mais le compilateur (GCC) n'apprécie pas du tout et me génère une erreur très vague : syntax error before '{' token
    ou syntax error before ' " ' token

    Je n'ai pas envie d'utiliser :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    user1.name[0] = 'N';
    user1.name[1] = 'O';
    // etc
    car ce n'est pas franchement pratique ! Comment faire alors ?

    Merci à vous pour votre aide

  10. #10
    Membre émérite
    Avatar de Pouet_forever
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    671
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 671
    Par défaut
    Je pense que c'est mieux de vider le buffer avec getchar, mais tu peux le faire d'autres manières aussi

    Plutôt que faire (*carmen).tour= tourDePoitrine; tu peux faire tout simplement carmen->tour = tourDePoitrine;

    Sinon pour le dernier point, ceci n'est valable qu'à la déclaration d'une chaîne de caractères. Si tu veux le faire par la suite, il faudra utiliser une fonction pour faire ça (strcpy) ou alors coder toi-même la fonction ^^
    Mettre le \0 dans "NON SAISI\0" est inutile, car quand tu déclares une chaîne de caractères entre guillemets, la chaîne ajoute automatiquement un \0 à la fin

  11. #11
    Inactif  
    Avatar de Mac LAK
    Profil pro
    Inscrit en
    Octobre 2004
    Messages
    3 893
    Détails du profil
    Informations personnelles :
    Âge : 51
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations forums :
    Inscription : Octobre 2004
    Messages : 3 893
    Par défaut
    Citation Envoyé par Pouet_forever Voir le message
    Je pense que c'est mieux de vider le buffer avec getchar, mais tu peux le faire d'autres manières aussi
    Cette méthode, normalement, marche partout en effet. Cependant, suivant la cible (et je précise qu'il faut CONNAITRE la cible pour en être certain !!), un "fflush(stdin);" peut être plus rapide, plus fiable, et/ou résoudre certains blocages partiellement aléatoires.

    Notamment, j'ai eu le souci sur une cible qui ne détectait pas correctement le EOF sur stdin... Donc, vider le buffer via getchar() provoquait une attente de touche s'il était déjà vide (!!), et ne fonctionnait correctement que s'il y avait déjà des caractères dans stdin. Bref, le bronx, corrigé parfaitement via un fflush sur stdin par contre.

    J'insiste lourdement : ce n'est pas standard de flusher stdin, ni portable, et c'est dépendant de compilateurs ne respectant pas complètement la norme C. Ceci étant dit, de tels compilateurs existent, sont encore utilisés, et il faut SAVOIR que le flush de stdin est PARFOIS la seule solution fiable. Donc, ne pas hurler dessus si l'on en croise, et ne pas l'enlever du code sans demander ni tester l'alternative, surtout sur du "vieux code".

    Par contre, pour un nouveau développement sur des plate-formes "connues" (Windows, Linux, MacOS) avec des compilateurs corrects (Visual, GCC aux dernières versions), c'est à proscrire et il vaut mieux se faire une petite routine de vidage à mettre dans sa librairie personnelle fourre-tout.
    Mac LAK.
    ___________________________________________________
    Ne prenez pas la vie trop au sérieux, de toutes façons, vous n'en sortirez pas vivant.

    Sources et composants Delphi sur mon site, L'antre du Lak.
    Pas de question technique par MP : posez-la dans un nouveau sujet, sur le forum adéquat.

    Rejoignez-nous sur : Serveur de fichiers [NAS] Le Tableau de bord projets Le groupe de travail ICMO

  12. #12
    Membre émérite
    Avatar de Pouet_forever
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    671
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 671
    Par défaut
    @Mac LAK : Ok je note
    Comme je n'ai jamais programmé sur autre chose que Mac, Linux et Windows je n'ai jamais eu ce problème

  13. #13
    Expert confirmé
    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
    Par défaut
    Mes profs nous encouragent à passer des pointeurs en paramètre des fonctions, plutot que de copier les variables localement aux fonctions (sans pointeur). Je pensais que c'était une bonne habitude à prendre.

    Dans un autre programme, je passe des pointeurs vers des structures en paramètre :...
    Ce n'est pas une habitude, c'est une question de nécessité ou d'efficacité
    - de nécessité , si on veut modifier par la liste des paramètres une variable de la fonction appelante
    - d'efficacité, si la variable passée est de grande taille parce que effectivement, ça évite une recopie. C'est donc parfaitement justifié dans l'exemple de ta structure, mais pas dans le cas d'un simple int. On peut utiliser dans ce cas le qualificatif const pour indiquer que le pointeur est sur un objet non modifiable par la fonction

    Hé bien j'ai pas mal galéré avant de me rendre compte par exemple qu'il faut bien ecrire (*carmen).tour= tourDePoitrine; sans oublier les parenthèses... ! J'imagine que c'est interprété différemment d'un compilateur à l'autre.
    Non, l'interprétation est la même sur tous les compilateurs : c'est une question de priorité des opérateurs. Comme dit dans le message de Pouet_forever, on utilise de préférence, car plus légère et plus courante, la notation carmen->tour

    Pour compléter ce que dit Pouet_forever sur le code :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    user1.name = {'N','O','N',' ','S','A','I','S','I','\0'};
    //ou
    user1.name = "NON SAISI\0";
    Comme le mentionnes ton cours, ceci sert à initialiser une chaîne et donc doit figurer au moment de la définition de la variable :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    char tab[]= {'N','O','N',' ','S','A','I','S','I','\0'};
    char tab[] = "NON SAISI";
    // mais attention
    char * tab = "NON SAISI";
    //met l'adresse de la chaîne NON MODIFIABLE "NON SAISI" dans tab

  14. #14
    Inactif  
    Avatar de Mac LAK
    Profil pro
    Inscrit en
    Octobre 2004
    Messages
    3 893
    Détails du profil
    Informations personnelles :
    Âge : 51
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations forums :
    Inscription : Octobre 2004
    Messages : 3 893
    Par défaut
    Citation Envoyé par Pouet_forever Voir le message
    @Mac LAK : Ok je note
    Comme je n'ai jamais programmé sur autre chose que Mac, Linux et Windows je n'ai jamais eu ce problème
    Il te manque le DOS, et certains compilos de l'époque...
    Mac LAK.
    ___________________________________________________
    Ne prenez pas la vie trop au sérieux, de toutes façons, vous n'en sortirez pas vivant.

    Sources et composants Delphi sur mon site, L'antre du Lak.
    Pas de question technique par MP : posez-la dans un nouveau sujet, sur le forum adéquat.

    Rejoignez-nous sur : Serveur de fichiers [NAS] Le Tableau de bord projets Le groupe de travail ICMO

  15. #15
    Membre émérite
    Avatar de Pouet_forever
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    671
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 671
    Par défaut
    Citation Envoyé par Mac LAK Voir le message
    Il te manque le DOS, et certains compilos de l'époque...
    Non, trop jeune pour ça

  16. #16
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    6
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 6
    Par défaut
    Je suis d'accord avec ça, et le compilateur aussi :

    Comme le mentionnes ton cours, ceci sert à initialiser une chaîne et donc doit figurer au moment de la définition de la variable :
    Code :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
     
    char tab[]= {'N','O','N',' ','S','A','I','S','I','\0'};
    char tab[] = "NON SAISI";
    // mais attention
    char * tab = "NON SAISI";
    //met l'adresse de la chaîne NON MODIFIABLE "NON SAISI" dans tab
    C'est idiot mais ce dernier ne veut pas entendre parler d'une telle déclaration dans une structure :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    struct personne {
     
    char name[41]="NON SAISI";    // cette ligne, c'est niet !  (error before = token)
    int codePostal;
     
    };
    A cause de cette difficulté je cherchais donc à faire ce que j'ai proposé :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    struct personne {
     
    char name[41];
    int codePostal;
     
    };
     
    void main(){
     
    struct personne user1;          // création d'une personne
    user1.name = "NON SAISI";    // Initialisation 1er champ     -> PAS OK
    user1.codePostal = -1;         // Initialisation 2eme champ   -> OK      
    }

  17. #17
    Membre émérite
    Avatar de Pouet_forever
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    671
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 671
    Par défaut
    Il ne faut rien affecter dans ta structure, il faut juste déclarer les variables.

    Comme dit précédemment il faut utiliser une fonction pour copier la chaîne dans user1.name.
    Ici j'utilise strcpy (cf google pour plus d'infos).

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    #include <string.h>
     
    struct personne {
    	char name[41];
    	int codePostal;
    };
     
    int main(void) {
    	struct personne user1;
    	strcpy(user1.name, "NON SAISI");
    	user1.codePostal = -1;
    	return 0;
    }

  18. #18
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    6
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 6
    Par défaut
    Oups, Désolé Pouet, j'ai manqué cette information dans ton message !

    Un grand merci à tous trois d'avoir été patients et super clairs je me sens plus fort

    Je continue mon petit bonhomme de chemin en C et j'espère prochainement vous revoir pour vous coller sur des problèmes d'IHM ou de jeux 3D en C

    Guillaume

  19. #19
    Expert confirmé
    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
    Par défaut
    C'est idiot mais ce dernier ne veut pas entendre parler d'une telle déclaration dans une structure :...
    Même principe : initialisation au moment de la définition de la variable :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    struct personne {
    	char name[41];
    	int codePostal;
    };
    ....
    struct personne user1 = { "NON SAISI", -1};

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

Discussions similaires

  1. [C#]Passage d'un parametre date a une procédure stocké
    Par frans2111 dans le forum Windows Forms
    Réponses: 2
    Dernier message: 28/08/2006, 23h07
  2. Probleme de passage d un parametre
    Par micanti dans le forum Struts 1
    Réponses: 6
    Dernier message: 07/07/2006, 17h03
  3. Passage de plusieurs parametre
    Par el_quincho dans le forum Access
    Réponses: 2
    Dernier message: 30/03/2006, 14h26
  4. Réponses: 7
    Dernier message: 27/03/2006, 16h18
  5. Réponses: 7
    Dernier message: 04/01/2005, 18h45

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