D'autres ont déjà dit certains problèmes spécifiques avec votre code, mais une chose qu'ils semblent avoir manqué est que c
devrait être un int
, non un char
. Sinon, la comparaison avec EOF
ne fonctionnera pas comme prévu.
En outre, le segfault que vous obtenez est à cause de cette séquence:
line[n++]=tmp;
printf("\n%s\n",line[n]);
Vous avez déjà incrémentée n
à l'autre élément de tableau, alors vous essayez de l'imprimer. Cette deuxième ligne devrait être:
printf("\n%s\n",line[n-1]);
Si vous voulez juste un code qui fonctionne (avec un libre « faire ce que vous voulez sacrément bien » licence), voici un extrait utile de ma bibliothèque de code.
Je ne suis pas sûr pourquoi vous pensez que fgets
est à éviter, c'est en fait très pratique et très sûr. Je suppose que vous vouliez dire gets
qui est moins pratique et totalement dangereux. Votre code est également sujet aux dépassements de tampon, car il écrira heureusement au-delà de la fin de votre zone allouée s'il reçoit beaucoup de caractères qui ne sont ni espace ni fin de fichier. Par tous les moyens, écrivez votre propre code si vous vous éduquez, mais une partie de cela devrait être l'examen du code pare-balles testé en production pour voir comment il peut être fait. Et, si vous êtes pas éduquer vous-même, vous vous faites un mauvais service en n'utilisant pas de code disponible gratuitement.
L'extrait suivant:
#include <stdio.h>
#include <string.h>
#define OK 0
#define NO_INPUT 1
#define TOO_LONG 2
static int getLine (char *prmpt, char *buff, size_t sz) {
int ch, extra;
// Get line with buffer overrun protection.
if (prmpt != NULL) {
printf ("%s", prmpt);
fflush (stdout);
}
if (fgets (buff, sz, stdin) == NULL)
return NO_INPUT;
// If it was too long, there'll be no newline. In that case, we flush
// to end of line so that excess doesn't affect the next call.
if (buff[strlen(buff)-1] != '\n') {
extra = 0;
while (((ch = getchar()) != '\n') && (ch != EOF))
extra = 1;
return (extra == 1) ? TOO_LONG : OK;
}
// Otherwise remove newline and give string back to caller.
buff[strlen(buff)-1] = '\0';
return OK;
}
// Test program for getLine().
int main (void) {
int rc;
char buff[10];
rc = getLine ("Enter string> ", buff, sizeof(buff));
if (rc == NO_INPUT) {
printf ("No input\n");
return 1;
}
if (rc == TOO_LONG) {
printf ("Input too long\n");
return 1;
}
printf ("OK [%s]\n", buff);
return 0;
}
Il est une fonction d'entrée de ligne utile qui a la même protection contre le débordement de la mémoire tampon comme fgets
et peut également détecter les lignes saisies par l'utilisateur qui sont trop longue. Il jette également le reste de la ligne trop longue pour ne pas affecter la prochaine opération d'entrée.
Sample fonctionne avec 'bonjour', CTRLD, et une chaîne qui est trop grand:
pax> ./qq
Enter string> hello
OK [hello]
pax> ./qq
Enter string>
No input
pax> ./qq
Enter string> dfgdfgjdjgdfhggh
Input too long
pax> _
Pour ce que ça vaut la peine (et ne remettre pas en tant que votre propre travail puisque vous serez presque certainement pris pour du plagiat - n'importe quel éducateur à moitié décent cherchera votre code sur le net comme la première chose qu'il fait), c'est ainsi que je l'aborderais.
#include <stdio.h>
#include <stdlib.h>
#define WORDLENGTH 15
#define MAXWORDS 1000
int main (void) {
char *line[MAXWORDS];
int numwords = 0; // Use decent variable names.
int chr, i;
// Code to run until end of file.
for (chr = getchar(); chr != EOF;) { // First char.
// This bit gets a word.
char *tmp = malloc(WORDLENGTH + 1); // Allocate space for word/NUL
i = 0;
while ((chr != ' ') && (chr != EOF)) { // Read until space/EOF
if (i < WORDLENGTH) { // If space left in word,
tmp[i++] = chr; // add it
tmp[i] = '\0'; // and null-terminate.
}
chr = getchar(); // Get next character.
}
line[numwords++] = tmp; // Store.
// This bit skips space at end of word.
while ((chr == ' ') && (chr != EOF)) {
chr = getchar();
}
}
// Now we have all our words, print them.
for (i = 0; i < numwords; i++){
printf ("%s\n", line[i]);
free (line[i]);
}
return 0;
}
Je vous suggère de lire cela et Studdy les commentaires afin que vous sachiez comment il fonctionne. N'hésitez pas à poser des questions dans la section des commentaires et je vais répondre ou clarifier.
Voici un échantillon analysé:
pax$ echo 'hello my name is pax andthisisaverylongword here' | ./testprog
hello
my
name
is
pax
andthisisaveryl
here
Ahhhh, je l'avais complètement oublié, mais je ne vais pas à nouveau! Toujours avoir le même problème si = – user527179
yep besoin de faire malloc (sizeof (char) * WORDLENGTH); –
sizeof (char) est garanti à 1 selon la norme. – EboMike