View Single Post
  #6 (permalink)  
Old 10-16-2007, 11:55 AM
G_Morgan G_Morgan is offline
Guru
 
Join Date: Oct 2007
Age: 24
Posts: 506
Last Blog:
Just over the next hil...
Rep Power: 10
G_Morgan has a spectacular aura aboutG_Morgan has a spectacular aura aboutG_Morgan has a spectacular aura about
Default

I'll comment on scanf since I think it's an awful function. Scanf expects data of the correct type. If you enter in the wrong data then it fails to work. Now you can catch this by catching the return code, scanf returns the number of items it read in so if it returns 0 you know that it failed on the first entry. You may think this appropriate

Code:
int check = 1;
int var = 0;
while(check){
    check = !scanf("%d", &var);
}
Since there's only one variable read, it will either return 0 on failure or 1 on success. The ! inverts this and check feeds it back into the while loop (so that this will loop until there is correct input).

You may think job done. Unfortunately scanf doesn't flush the input buffer on failure so if I enter 'error' it will stay on the input buffer for the next time, this program gives an infinite loop on an error.

So what can we do? We could call fflush(stdin); but this behaviour is undefined according to the C standard. Windows happens to define fflush on stdin but I've seen code elsewhere which doesn't work.

Personally I prefer to use fgets.
Code:
char buff[20];
fgets(buff, size, stdin);
and then parse the output. It certainly doesn't leave mess on stdin and is fully portable. Once you've got a set of functions written to do this you won't ever need to touch temperamental scanf again. The one thing to be careful of, fgets leaves the newline character on the end of the output so you will want to write a function that scans it and replaces it with the null character.
Reply With Quote