Reputation: 48
I have a very simple code segment where there is a do while loop with a switch case which goes as follows:
do {
printf("Enter Choice\n");
scanf("%d", &choice);
switch(choice) {
case 1: printf("1 selected");
break;
case 2: printf("exit");
break;
default: printf("wrong input");
break;
}
} while (choice != 2);
In this piece of code if by accident I enter a character instead of a number the program goes haywire looping indefinitely and doesnt even take the input. I know this can be corrected if I insert
if(isdigit(choice))
before getting into switch case. But my question is why does it happen in the first place.
Shouldn't it go to default case and ask for input again?
Upvotes: 0
Views: 2342
Reputation: 1
I tried if(isdigit(choice)) but problem remain as it is. This issue is related with buffer if datatype of input doesnt match with format specifier in scanf then input is not consume by scanf and remain in buffer.
To solve this issue I tried fflush(stdin) which works fine for c compiler in windows but not working on linux ,sorry I dont know the reason why fflush(stdin) not working on linux.
I also tried getchar() which work fine on windows and linux, I put getchar() at end of statement inside loop .
do
{
printf("Enter Choice\n");
scanf("%d", &choice);
switch(choice) {
case 1: printf("1 selected");
break;
case 2: printf("exit");
break;
default: printf("wrong input");
break;
}
getchar();
} while (choice != 2);
Upvotes: 0
Reputation: 182619
If scanf
can't match input with the format specifier, it leaves it in the buffer. So the next time around it still won't match and so on. In other words, it doesn't eat what it can't match. You must check the value returned by scanf
, the number of matched items, to make sure the input was expected.
Alternatively, to skip unwanted stuff, you could try (untested):
scanf("%*[^0-9]%d", &choice);
This should discard anything that's not a digit before trying to read a decimal integer.
Upvotes: 5
Reputation: 59997
Please checkout the scanf manual page.
If the next thing in the input is not a number in this case it does not consume it.
You need to check the return value from scanf
and if it is zero, consume the next character and try again (or perhaps until end of line is reached).
Upvotes: 1