This question has been asked before, but i've never found a clear and simple answer, so i'm asking it again...
I'de li开发者_如何学编程ke to know, without using any other library than stdio.h, how to check if what the user has entered is a numeric value or not. Basically, the user is asked to enter a value between 0 and 9. If the number is between those two, it continues. If the number is 12 for example, it loops back to the question and asks for the number again.
It works fine, except that if i enter a letter OR a decimal number, it enters into an infinite loop...
Basically here is my question: how can i check that the value entered is not a character and non decimal?
Here is the beginning of the code: (sorry, its in french, but you get the idea...)
int main()
{
int nb1, nb2, rand_1, rand_2;
int nb_coups = 0;
int points = 0;
printf("\n\n ------ BIENVENUE A LA GRANDE ROUE ! ------\n\n");
do{
//Saisie 1er nombre
printf("Entrez le premier nombre choisi (entre 0 et 9) : ");
scanf("%d",&nb1);
//Tant que le 1er nombre n'est pas compri entre 0 et 9, on le redemande
while(nb1<0 || nb1>9)
{
printf("Nombre incorrect. Entrez le premier nombre choisi (entre 0 et 9) : ");
scanf("%d",&nb1);
}
//On affiche le 1er nombre
printf("Le nombre choisi est : %d\n\n",nb1);
Don't use scanf() for console input. Instead, use fgets() to read data from stdin into a string and then parse that, or use getchar() to read a character at a time. If your environment includes such a thing, you might also consider getch() which, when supported, will generally read a typed character without waiting for a return afterward.
With fgets and sscanf:
char line [16];
fprintf(stderr, "Entrez le premier nombre choisi (entre 0 et 9) : ");
fgets (line, sizeof(line), stdin);
ret = sscanf(line,"%d",&nb1);
//Tant que le 1er nombre n'est pas compri entre 0 et 9, on le redemande
while((ret == 0) || (nb1 < 0) || (nb1 > 9)) {
fprintf(stderr, "Nombre incorrect. Entrez le premier nombre choisi (entre 0 et 9) : ");
fgets (line, sizeof(line), stdin);
ret = sscanf(line,"%d",&nb1);
}
You should check the return value to weed out non-numbers.
printf("Entrez le premier nombre choisi (entre 0 et 9) : ");
ret = scanf("%d",&nb1);
//Tant que le 1er nombre n'est pas compri entre 0 et 9, on le redemande
while(!ret && (nb1<0 || nb1>9))
{
char ch;
while ((ch = getchar()) != '\n' && ch != EOF); // Flush the buffer
printf("Nombre incorrect. Entrez le premier nombre choisi (entre 0 et 9) : ");
ret = scanf("%d",&nb1);
}
Don't use scanf, do the parsing yourself.
char c;
int nb1 = 0;
while(1) {
c = getchar();
if(c > '0' && c < '9') {
nb1 = nb1*10 + (c - '0'); // if you want numbers bigger than 9
}
else {
break; // matches '\n', invalid chars and EOF
}
}
Voila!
I like general purpose:
General purpose, with some overflow protection, and allows some generality, if you like a different range.
#include <ctype.h>
int atoi(char *s, int N)
{
int n; /* value being accumulated */
int sign; /* =1 if result is positive, -1 if negative */
while((N>0)&&(*s == '\t' || *s == ' '))
{
N--;
s++; /* skip white space */
}
sign=1; /* assume a positive value */
if(*s == '+' || *s == '-')
{
N--;
sign = *s++ == '-' ? -1 : 1; /* adjust result sign */
}
for(n=0; (N>0)&&isdigit(*s); s++,N--)
n = n * 10 + *s - '0';
return (sign * n); /* result adjusted for sign */
}
精彩评论