2012-12-31 5 views
4

dans une programmation C son étant donné que nous ne pouvons pas obtenir les valeurs en utilisant la fonction scanf() pour tableau de pointeurs, maistableau de pointeurs vers des chaînes

int main() 
{ 
char *names[6]; 
int loop; 
scanf("%s",names[1]); 
printftf("\n%s",names[1]); 
} 

il travaille, quand je donne l'entrée en tant que programme , je pense qu'il stocke l'entrée, mais elle imprime la sortie correctement comme donnée input.after qui lui donne une erreur de segmentation ... mais quand je fais la même chose dans une boucle pour obtenir 6 charecters

int main() 
{ 
char *names[6]; 
int loop; 
for(loop=0;loop<6;loop++) 
scanf("%s",names[1]); 
for(loop=0;loop<6;loop++) 
printf("\n%s",names[1]); 
} 

son ne fonctionne pas s'il vous plaît donnez-moi la réponse ...

Répondre

11

Le problème est que vous n'allouez aucun espace pour les noms . Vous devez initialiser chaque élément du tableau si vous avez l'intention de l'utiliser avec scanf.

char* names[6]; 
for(int i = 0; i < 6; ++i) 
    names[i] = malloc(256 * sizeof *names[i]); // or some other max value 

scanf("%s", names[1]); 

Sinon, ces pointeurs pointera partout dans votre mémoire, et la tentative de lecture/écriture de ces endroits finiront par se traduire par une erreur de segmentation .

+0

Bonne réponse, K-ballo. Bien que le code original soit un exemple plutôt trivial, il est toujours recommandé de vérifier les retours NULL de malloc pour intercepter les conditions de mémoire insuffisante: if ((noms [i] = malloc (256 * sizeof (char)) == NULL) {fprintf (stderr, "Erreur d'allocation! \ n"); exit (1)}. –

+2

Est-ce que 'sizeof * names [0]' serait mieux ici que 'sizeof (char)'? De cette façon, il suit le type réel, – jthill

+0

D'autant plus que 'sizeof (char)' est 1. –

3

Dans votre code names est un tableau de 6 pointeurs sur char. Maintenant, chacun de ces pointeurs peut stocker le point de départ (l'adresse du premier caractère) d'une nouvelle chaîne. Cela signifie que vous pouvez stocker les adresses de départ de 6 différentes chaînes dans votre variable names. Mais quand vous utilisez une boucle pour initialiser chacune de ces chaînes, vous devez indiquer à la machine combien de temps chaque chaîne peut être, afin qu'elle puisse allouer un bloc continu d'adresses dont la première adresse peut être stockée dans votre pointeur à référez à votre chaîne. Ainsi, vous devez allouer une certaine taille que vous pensez devrait être suffisante pour stocker votre chaîne (par exemple: 256 octets, 1 octet étant 1 caractère). En l'absence de cela, la machine ne sait pas où stocker tous les octets de votre chaîne et lance une erreur de segmentation due à un accès mémoire illégal.

Pour ce faire, chacun de vos 6 pointeurs doit avoir de l'espace pour stocker une chaîne. Cela sera fait dans votre boucle en utilisant malloc(). Basé sur le code de @ K-ballo:

char* names[6]; 
int max_length = 256; // The maximum length you expect 
for(int i = 0; i < 6; ++i) 
    names[i] = malloc(max_length * sizeof(char)); // allocates max_length number of bytes 

scanf("%s", names[1]); 

Alors maintenant, vous avez essentiellement un 6 différents blocs d'adresses max_length char continu qui sont appelés chacun par names[i]. Quand vous faites le scanf() il lit les octets de l'entrée standard et met alors dans ces octets alloués dans la mémoire visée par des noms [1].

J'ai eu du mal au début à comprendre tout cela, alors je pensais qu'une explication compliquée aiderait. :)

Questions connexes