How can I get my program to ignore character inputs?

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;
} 
Thanks, that helped!

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...
The best option is to do it in one statement!


1
2
while ((c=getchar())==isalpha(c))
;
Perhaps you should make an input function rather than using cin directly in your code.
 
int getInt(int min, int max);


Then input would be:
 
int num = getInt(1, 2);


Rather than:
1
2
3
4
5
while(!cin || (num<=0 || num>=3))
{
    cout << "Invalid entry. Number must be 1 or 2. Please reenter number: ";
    cin >> num;
}


The body of getInt() would be pretty similar to the latter.
How about making a function?

1
2
3
#include <iostream>
#include <sstream>
#include <string> 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
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;

    else if ((minimum_value > result) or (result > maximum_value))
      std::cout << bad_range_message;

    else break;
    }

  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";

Hope this helps.
I did what Duoas sugested in the thread that hamsterman linked me to:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40

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...
Last edited on
FYI, this is another great link for stdio FAQs.
http://www.parashift.com/c++-faq-lite/input-output.html
Topic archived. No new replies allowed.