An up to date book should cover std::stoi() -- it is one of a related set of conversions functions which was introduced in C++11.
As it stands, it is a bit hacky. You ideally need to check the value you get from the user and then give them a chance to correct their mistake.
To make your code robust, the first step is to refactor the code to use a function to read the int value (I started off from newbiee999's code above, but value1 and value2 are now back to ints.)
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
|
#include "std_lib_facilities.h"
bool get_int_value(const string& prompt, int& value);
int main()
{
int value1 = 0;
int value2 = 0;
bool more = 0; // "continue" is a keyword
do
{
more = get_int_value("Input value1", value1);
if(more)
more = get_int_value("Input value2", value2);
if(more)
cout << "Value1 is: " << value1 << " and Value2 is: " << value2 << "\n";
}
while(more);
return 0;
}
bool get_int_value(const string& prompt, int& value)
{
cout << prompt << ": ";
string str;
cin >> str;
if (str == "|")
return false;
value = stoi(str, nullptr, 0);
return true;
}
|
As it stands, the code can't handle bad input, e.g.
Input value1: 1
Input value2: 2
Value1 is: 1 and Value2 is: 2
Input value1: 3
Input value2: a
terminate called after throwing an instance of 'std::invalid_argument'
what(): stoi
This application has requested the Runtime to terminate it in an unusual way.
Please contact the application's support team for more information. |
(this test app was built with the MinGW version of GCC 4.8.1)
But by adding some exception handling code and a while loop to get_int_value()
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
|
bool get_int_value(const string& prompt, int& value)
{
while(true)
{
cout << prompt << ": ";
string str;
cin >> str;
if (str == "|")
return false;
try
{
value = stoi(str, cha, 0);
return true;
}
catch(invalid_argument)
{
cout << "Error: Invalid value. Please enter either\n"
"a valid integer value or | to quit.\n";
}
}
}
|
It can now handles the error that cause grief above:
Input value1: 1
Input value2: 2
Value1 is: 1 and Value2 is: 2
Input value1: 3
Input value2: a
Error: Invalid value. Please enter either
a valid integer value or | to quit.
Input value2: 4
Value1 is: 3 and Value2 is: 4
Input value1: | |
But get_int_value() is still incomplete...
Input value1: 1
Input value2: 2
Value1 is: 1 and Value2 is: 2
Input value1: 3apples
Input value2: 4pears
Value1 is: 3 and Value2 is: 4
Input value1: 3.1415
Input value2: 2.5
Value1 is: 3 and Value2 is: 2
Input value1: a
Error: Invalid value. Please enter either
a valid integer value or | to quit.
Input value1: 3 a
Input value2: Error: Invalid value. Please enter either
a valid integer value or | to quit.
Input value2: a 3
Error: Invalid value. Please enter either
a valid integer value or | to quit.
Input value2: Value1 is: 3 and Value2 is: 3
Input value1: 12345678910121212
terminate called after throwing an instance of 'std::out_of_range'
what(): stoi
This application has requested the Runtime to terminate it in an unusual way.
Please contact the application's support team for more information. |
- modifying get_int_value() to reject "3apples", 3.1415, etc requires the second parameter of std::stoi to be checked (to see how much of the string was converted.)
- the function needs to be modified so it doesn't extract both numbers from one input line
- handling the std::out_of_range exception as well will protect the code against overlarge numbers.
Andy