I read here that feof or more precisely using !feof in searching for a info in a file is a bad habit.
What I understood is that it's bad because it reads information from the FILE pointer before called function or process or something like that.
Wouldn't it be fine to have a do/while loop with fscanf inside and !feof as the exit condition?
This is a search function that I did:
typedef struct
{
char lname[20] , fname[20];
int nchildren;
}employee;
void searchemployee(char *filename , char *str)
{
employee e;
FILE *f;
int c;
f = fopen(filename, "r");
if (f == NULL)
printf("file couldn't be loaded\n");
else {
c = 0;
do {
fscanf(f, "%s %s %d\n", e.fname, e.lname, &e.nchildren);
if (strcmp(e.fname, str) == 0)
c = 1;
} while (c == 0 && !feof(f));
if (c != 1)
printf("employee not found\n");
else
printf("employee : %s %s| children : %d\n", e.fname, e.lname, e.nchildren);
}
fclose(f);
}
The return value of the function
feofspecifies whether a previous input operation has already encountered the end of the file. This function does not specify whether the next input will encounter the end of the file.The problem with
is that if
fscanffails and returnsEOFdue to encountering the end of the file, then it will write nothing toe.fname.If this happens in the first iteration of the loop, then the content of
e.fnamewill be indeterminate and the subsequent function callstrcmp(e.fname,str)will invoke undefined behavior (i.e. your program may crash), unlesse.fnamehappens to contain a terminating null character.If this does not happen in the first iteration, but rather in a subsequent iteration of the loop, then the content of
e.fnamewill contain the content of the previous loop iteration, so you will effectively be processing the last successful call offscanftwice.In this specific case, processing the last successful call of
fscanftwice is harmless, except for being a slight waste of CPU and memory resources. However, in most other cases, processing the last input twice will result in the program not working as intended.See the following question for further information:
Why is “while( !feof(file) )” always wrong?
If you change the loop to
so that the loop condition is checked in the middle of the loop, then the problem mentioned above will be gone.
However, it is generally better to check the return value of
fscanfinstead of callingfeof, for example like this:Also, you don't need the flag variable
c. I suggest that you incorporate the linespartially into the loop, like this:
Another issue is that when using
%swithscanforfscanf, you should generally also add a width limit, to prevent a possible buffer overflow. For example, ife.fnamehas a size of100characters, you should use%99sto limit the number of bytes written to99plus the terminating null character.