Programmation en c, erreur de segmentation
Fermé
allezlolo
-
25 avril 2008 à 22:18
mype Messages postés 2435 Date d'inscription jeudi 1 novembre 2007 Statut Membre Dernière intervention 16 août 2010 - 26 avril 2008 à 00:24
mype Messages postés 2435 Date d'inscription jeudi 1 novembre 2007 Statut Membre Dernière intervention 16 août 2010 - 26 avril 2008 à 00:24
A voir également:
- Programmation en c, erreur de segmentation
- Erreur 0x80070643 - Accueil - Windows
- Application de programmation - Guide
- Erreur 0x80070643 Windows 10 : comment résoudre le problème de la mise à jour KB5001716 - Accueil - Windows
- Erreur 1001 outlook - Accueil - Bureautique
- Instagram une erreur s'est produite ✓ - Forum Instagram
7 réponses
kilian
Messages postés
8732
Date d'inscription
vendredi 19 septembre 2003
Statut
Modérateur
Dernière intervention
5 février 2025
1 526
25 avril 2008 à 22:44
25 avril 2008 à 22:44
Alors je viens de tester et j'ai aucun soucis avec ce programme:
J'entre prout pour le jom de l'équipe et bidule pour le nom du coach.
#include <stdlib.h> #include <stdio.h> typedef struct equipe { char *nom; char* tab[24]; }equipe; void lireEquipe(equipe *e) { printf ("Entrez le nom de l'équipe : "); e -> nom = (char*) malloc (sizeof(char)*50); scanf ("%s",e->nom); //Tout simplement ;-) printf ("Entrez le nom du coach : "); //Attention e->tab[0] ne pointe sur rien! //Alors on alloue e->tab[0] = (char *) malloc(sizeof(char) * 50); scanf ("%s",e -> tab[0]); } int main() { equipe *e; e = (equipe*) malloc (sizeof(equipe)); lireEquipe(e); return 0; }
J'entre prout pour le jom de l'équipe et bidule pour le nom du coach.
kilian
Messages postés
8732
Date d'inscription
vendredi 19 septembre 2003
Statut
Modérateur
Dernière intervention
5 février 2025
1 526
25 avril 2008 à 22:30
25 avril 2008 à 22:30
e->nom est déjà un pointeur, donc pas besoin d'utiliser le signe &
Idem pour e->tab[0]
A part ça un petit oubli d'allocation, sinon ça va.
Idem pour e->tab[0]
A part ça un petit oubli d'allocation, sinon ça va.
void lireEquipe(equipe *e) { printf ("Entrez le nom de l'équipe : "); e -> nom = (char*) malloc (sizeof(char)*50); scanf ("%s",e->nom); //Tout simplement ;-) printf ("Entrez le nom du coach : "); //Attention e->tab[0] ne pointe sur rien! //Alors on alloue e->tab[0] = (char *) malloc(sizeof(char) * 50); scanf ("%s",e -> tab[0]); }
Merci kilian mais j'ai toujours la même ererur avec un copier coller de ce que tu m'as donné,(j'avais déjà essayé auparavant)
voici mon main si ça peut t'aider.
int main() {
equipe *e;
e = (equipe*) malloc (sizeof(equipe));
lireEquipe(e);
}
merci
voici mon main si ça peut t'aider.
int main() {
equipe *e;
e = (equipe*) malloc (sizeof(equipe));
lireEquipe(e);
}
merci
merci de ta réponse, en fait l'erreur vient d'une autre fonction
mon main est exactement
int main() {
score *s;
equipe *e;
e = (equipe*) malloc (sizeof(equipe));
// s = lireScore();
lireEquipe(e);
printf("equipe lu");
// afficherScore(s);
afficherEquipe(e);
//printf("%d",compareScore(s));
}
et c'est en fait afficherEquipe(e) qui fait planter car quand je l'enlève cela fonctionne.
C'est bizarre parce que au début je n'avais même pas "equipe lu" qui s'affiché mais directement l'erreur, maintenant que j'ai mis afficherEquipe entre commentaires ça marche.
Toutefois, j'ai encore une ptit problème avec afficherEquipe, voici ma fonction
void afficherEquipe (equipe *e) {
printf ("Nom de l'équipe : %s",*(e -> nom));
printf ("Nom du coach : %s",*(e -> tab[0]));
/* int i = 1; */
/* char *vide = "vide"; */
/* while ( i != 24) { */
/* if (strcmp(e->tab[i],vide)) { */
/* printf("Joueur numéro %d : Maillot non attribué"); */
/* } else { */
/* printf("Joueur numéro %d : %s",i+1 ,e->tab[i]); */
/* } */
/* } */
}
je ne comprends pas pourquoi cela ne fonctionne pas, c'est assez prise de tête lol.
merci tu me rends bien service ;)
mon main est exactement
int main() {
score *s;
equipe *e;
e = (equipe*) malloc (sizeof(equipe));
// s = lireScore();
lireEquipe(e);
printf("equipe lu");
// afficherScore(s);
afficherEquipe(e);
//printf("%d",compareScore(s));
}
et c'est en fait afficherEquipe(e) qui fait planter car quand je l'enlève cela fonctionne.
C'est bizarre parce que au début je n'avais même pas "equipe lu" qui s'affiché mais directement l'erreur, maintenant que j'ai mis afficherEquipe entre commentaires ça marche.
Toutefois, j'ai encore une ptit problème avec afficherEquipe, voici ma fonction
void afficherEquipe (equipe *e) {
printf ("Nom de l'équipe : %s",*(e -> nom));
printf ("Nom du coach : %s",*(e -> tab[0]));
/* int i = 1; */
/* char *vide = "vide"; */
/* while ( i != 24) { */
/* if (strcmp(e->tab[i],vide)) { */
/* printf("Joueur numéro %d : Maillot non attribué"); */
/* } else { */
/* printf("Joueur numéro %d : %s",i+1 ,e->tab[i]); */
/* } */
/* } */
}
je ne comprends pas pourquoi cela ne fonctionne pas, c'est assez prise de tête lol.
merci tu me rends bien service ;)
Vous n’avez pas trouvé la réponse que vous recherchez ?
Posez votre question
kilian
Messages postés
8732
Date d'inscription
vendredi 19 septembre 2003
Statut
Modérateur
Dernière intervention
5 février 2025
1 526
25 avril 2008 à 23:02
25 avril 2008 à 23:02
C'est bizarre parce que au début je n'avais même pas "equipe lu" qui s'affiché mais directement l'erreur, maintenant que j'ai mis afficherEquipe entre commentaires ça marche.
Si tu fais un printf et qu'il y a une erreur juste après, parfois ton printf n'affiche pas. C'est normal, quand tu envoies quelque chose à printf, ça peut rester quelques temps dans la mémoire avant d'être écrit sur l'écran.
Si tu veux être sûr que ton printf s'affiche direct, balance juste derrière:
Ca vide la mémoire et écris à l'écran.
Passons à ta fonction.
Pourquoi tu fais ça:
e->nom est de type char *
C'est un pointeur vers une chaine de caractères. C'est justement ce que demande le "%s" du printf.
Si tu fais *(e->nom) tu vas chercher le premier caractère de cette chaine et ça va planter car c'est pas une adresse mais un caractère.
Même chose pour e->tab[0]
Si tu fais un printf et qu'il y a une erreur juste après, parfois ton printf n'affiche pas. C'est normal, quand tu envoies quelque chose à printf, ça peut rester quelques temps dans la mémoire avant d'être écrit sur l'écran.
Si tu veux être sûr que ton printf s'affiche direct, balance juste derrière:
fflush(stdout);
Ca vide la mémoire et écris à l'écran.
Passons à ta fonction.
Pourquoi tu fais ça:
*(e -> nom)
e->nom est de type char *
C'est un pointeur vers une chaine de caractères. C'est justement ce que demande le "%s" du printf.
Si tu fais *(e->nom) tu vas chercher le premier caractère de cette chaine et ça va planter car c'est pas une adresse mais un caractère.
Même chose pour e->tab[0]
Merci de ta réponse,
en effet cela marche.
Le problème est que je crois ne pas avoir encore tout compris (boulet...)
En fait si je fais
int i = 3;
printf("%d",i);
Cela marche est mon i n'ai pas un pointeur (différent de int*i).
Et dans notre cas précis tu me dis qu'il faut mettre (equipe->nom) car il nous est demandé un pointeur.
Cela dépendrait t'il du %d qui attend une valeur ?et du %s qui attend un pointeur. ?
J'ai du mal à comprendre ces différences :s
en effet cela marche.
Le problème est que je crois ne pas avoir encore tout compris (boulet...)
En fait si je fais
int i = 3;
printf("%d",i);
Cela marche est mon i n'ai pas un pointeur (différent de int*i).
Et dans notre cas précis tu me dis qu'il faut mettre (equipe->nom) car il nous est demandé un pointeur.
Cela dépendrait t'il du %d qui attend une valeur ?et du %s qui attend un pointeur. ?
J'ai du mal à comprendre ces différences :s
kilian
Messages postés
8732
Date d'inscription
vendredi 19 septembre 2003
Statut
Modérateur
Dernière intervention
5 février 2025
1 526
25 avril 2008 à 23:30
25 avril 2008 à 23:30
Voilà. En fait quand tu mets %d il attend un entier. Donc une valueur immédiate et pas une adresse (un pointeur).
Quand tu mets %s il attend une chaine de caractère. Donc un pointeur ou un tableau.
Par contre avec scanf les choses changent avec %d.
Si tu fais un scanf("%d", i);
ca ne marchera pas si i est un entier. Car pour que scanf puisse placer la valeur qu'on va lui donner dans i, il faut lui passer l'adresse de i. Ce ne serait pas possible autrement: quand tu passe un entier en paramètre d'une fonction, tu ne fais que passer sa valeur, mais la variable en elle même tu ne pourra plus l'atteindre dans cette fonction. Il te faut donc son adresse (qui est de type int *). C'est pourquoi il faudrait mettre
scanf("%d", &i);
Alors que pour uen chaine de caractère pas besoinde mettre le signe &, car une chaine de caractère c'est déjà un pointeur (donc une adresse).
Tu saisis? N'hésite pas si tu as des questions.
Quand tu mets %s il attend une chaine de caractère. Donc un pointeur ou un tableau.
Par contre avec scanf les choses changent avec %d.
Si tu fais un scanf("%d", i);
ca ne marchera pas si i est un entier. Car pour que scanf puisse placer la valeur qu'on va lui donner dans i, il faut lui passer l'adresse de i. Ce ne serait pas possible autrement: quand tu passe un entier en paramètre d'une fonction, tu ne fais que passer sa valeur, mais la variable en elle même tu ne pourra plus l'atteindre dans cette fonction. Il te faut donc son adresse (qui est de type int *). C'est pourquoi il faudrait mettre
scanf("%d", &i);
Alors que pour uen chaine de caractère pas besoinde mettre le signe &, car une chaine de caractère c'est déjà un pointeur (donc une adresse).
Tu saisis? N'hésite pas si tu as des questions.
Excellent je comprends beaucoup plus et beaucoup mieux, c'est bizarre parce que je sors de presque deux ans de Pascal et j'ai plutôt du mal à me faire au c mais après réflexion cela ressemble pas mal.
Je vais abuser avec une dernière question lol, par hasard existe t-il une fonction du style de scanf me permettant d'envoyer une chaine de caractère avec des espaces ?
merci pour tout
Je vais abuser avec une dernière question lol, par hasard existe t-il une fonction du style de scanf me permettant d'envoyer une chaine de caractère avec des espaces ?
merci pour tout
mype
Messages postés
2435
Date d'inscription
jeudi 1 novembre 2007
Statut
Membre
Dernière intervention
16 août 2010
436
>
allezlolo
25 avril 2008 à 23:40
25 avril 2008 à 23:40
oui fgets()...
kilian
Messages postés
8732
Date d'inscription
vendredi 19 septembre 2003
Statut
Modérateur
Dernière intervention
5 février 2025
1 526
>
allezlolo
25 avril 2008 à 23:53
25 avril 2008 à 23:53
gets() pour être plus précis.
Ou fgets:
fgets est moins dangereuse à utiliser car tu peux lui donner une limite de nombre de caractères.
char s[50]; gets(s);
Ou fgets:
char s[50]; fgets(s, 49, stdout);
fgets est moins dangereuse à utiliser car tu peux lui donner une limite de nombre de caractères.
mype
Messages postés
2435
Date d'inscription
jeudi 1 novembre 2007
Statut
Membre
Dernière intervention
16 août 2010
436
>
kilian
Messages postés
8732
Date d'inscription
vendredi 19 septembre 2003
Statut
Modérateur
Dernière intervention
5 février 2025
25 avril 2008 à 23:56
25 avril 2008 à 23:56
oui c'est vrai gets() marche aussi mais est deconseillé car il ne verifie pas s'il y a un debordement de la chaine...
avec fgets() on peut definir le nombre de caractere a stocké pour etre sur de ne pas débordé
avec fgets() on peut definir le nombre de caractere a stocké pour etre sur de ne pas débordé
kilian
Messages postés
8732
Date d'inscription
vendredi 19 septembre 2003
Statut
Modérateur
Dernière intervention
5 février 2025
1 526
>
mype
Messages postés
2435
Date d'inscription
jeudi 1 novembre 2007
Statut
Membre
Dernière intervention
16 août 2010
26 avril 2008 à 00:00
26 avril 2008 à 00:00
C'est vrai, d'ailleurs j'ai édité mon message, c'est pas un truc à conseiller à un débutant... :-)