Reading names in a file in C

I have a file like this:

name1 nickname1 name2 nickname2 name3 nickname3 

And I want my program to read this file and show the name / nicknames pairs.

Here is what I did:

 users_file = fopen("users", "r"); while(!feof(users_file)) { fscanf(users_file, "%s %s", &user.username, &user.name); printf("%s | %s\n", user.username, user.nickname); } 

And here is the conclusion:

  name1 | nickname1 name2 | nickname2 name3 | nickname3 name3 | nickname3 

Why is the latter repeated? Thanks

+4
source share
3 answers

You need to check feof() immediately after fscanf() or, conversely, check the return value from fscanf() . The latter is repeated because fscanf() does not read any new data in user.username and user.nickname due to reaching eof.

Possible fixes:

 /* * You could check that two strings were read by fscanf() but this * would not detect the following: * * name1 nickname1 * name2 nickname2 * name3 nickname3 * name4 * name5 * * The fscanf() would read "name4" and "name5" into * 'user.username' and 'user.name' repectively. * * EOF is, typically, the value -1 so this will stop * correctly at end-of-file. */ while(2 == fscanf(users_file, "%s %s", &user.username, &user.name)) { printf("%s | %s\n", user.username, user.nickname); } 

or

 /* * This would detect EOF correctly and stop at the * first line that did not contain two separate strings. */ enum { LINESIZE = 1024 }; char line[LINESIZE]; while (fgets(line, LINESIZE, users_file) && 2 == sscanf(line, "%s %s", &user.username, &user.name)) { printf("%s | %s\n", user.username, user.name); } 
+3
source

If you change your loop to this:

 while((fscanf(users_file, "%s %s", &user.username, &user.name)) { printf("%s | %s\n", user.username, user.nickname); } 

Then this should work, note that we do not check EOF, we allow fscanf to check it for us.

+1
source

The feof() function returns true if the end-of-file state has been viewed. This is probably not the case if you are reading from a file.

There are several ways to get around this, something that migtht works (and, in fact, what hmjd says):

 while (fscanf(users_file, "%s %s", &user.username, &user.name) == 2) { ... } 

The return value of fscanf is the number of successfully converted and assigned conversions, so if you get EOF while reading, it will be different than expected.

0
source

Source: https://habr.com/ru/post/1400407/


All Articles