I am trying to set up a menu for which you are presented with 2 options (1 or 2). If a different number is typed, I got it so that the program rejects it. However, if an alpha character is typed, the program just wigs out. How can I get it to ignore alpha characters and only accept numbers?
This is a common question so I'll just link to an older post of mine. http://www.cplusplus.com/forum/beginner/28223/#msg151683
Though there might be cleaner ways to write it..
Anyway, the idea is to evaluate cin>>to a boolean and cin.clear and retry if it's a 0. Alternatively you could use cin.fail to find an error.
I wrote this code to test OP's question and for some reason when a character other than a number is entered, it causes an infinite loop. I am not sure why though...
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
int main()
{
int num;
cout << "Please enter 1 or 2: ";
cin >> num;
while(!cin || (num<=0 || num>=3))
{
cout << "Invalid entry. Number must be 1 or 2. Please reenter number: ";
cin >> num;
}
return 0;
}
Unforunately, there are lots of places in my program that require the input of numbers, and I dont want to copy that whole code all over my program. I'm sure I can figure out an easier way of doing it if I sat here and thought about it...
template <typename Result>
Result get_input(
Result default_value,
Result minimum_value,
Result maximum_value,
const std::string& start_message,
const std::string& try_again_message,
const std::string& bad_range_message
) {
Result result( default_value );
std::cout << start_message;
while (true)
{
std::string s;
std::getline( std::cin, s );
s.erase( s.find_last_not_of( " \f\n\r\t\v" ) + 1 );
if (s.empty()) break;
std::istringstream ss( s );
ss >> result;
if (!ss.eof())
std::cout << try_again_message;
elseif ((minimum_value > result) or (result > maximum_value))
std::cout << bad_range_message;
elsebreak;
}
return result;
}
Use it thusly:
1 2 3 4 5 6 7 8 9
int x = get_input(
50,
1,
100,
"I am thinking of a number between 1 and 100, inclusive.\nWhat is it? ",
"That was not a number. Try again: ",
"The number must be between 1 and 100, inclusive: "
);
cout << "Good job! You guessed the number " << x << ".\n";
int main()
{
switch (menu())
{
case 1:
//blahblah
break;
case 2:
//blahblah
break;
default:
//blahblah
}
}
int menu()
{
int x;
cin>>x;
while (true)
{
if (!cin)
{
cin.clear();
cin.ignore( numeric_limits <streamsize> ::max(), '\n');
cout << "\nThat was a letter. Letters are not numbers.\n\nTry Again:\n\n";
}
else
{
cin.ignore( numeric_limits <streamsize> ::max(), '\n');
break;
}
}
return x;
}
It's a bit cumbersome, but it got the job done.
EDIT: I had a hell of a time trying to get the source code box to format correctly (still looks crappy). It didnt copy well from my compiler. Sorry it's so...spacey...