我编写了一些代码,用于检查用户是否使用while循环输入了正确的输入类型。问题是,在输入每个错误字符后,它会再次重新循环。
但是当你输入多个字符时,它会一次又一次地循环相同的cout
语句。例如,如果我键入" qwerty",当我只希望它运行一次时,它会输出那些
cout`语句6次。
代码如下:
#include <iostream>
using namespace std;
int main(){
// Declare the variables
int choice = 0;
bool valid = false;
while(!valid){
valid = true;
//Ask the user for their choice
cout << "Which function would you like to use? \n";
cout << "1) Average Function \n";
cout << "2) Mean Absolute Deviation Function \n";
cout << "3) Number Sorting Function \n";
cout << "4) Median Function \n";
cout << "5) All of the above \n";
cout << "6) Calculator Function \n";
cout << "Your choice: ";
cin >> choice;
if(cin.fail() || choice > 6 || choice < 1){
cout << "ERROR, PLEASE ENTER ONLY VALID SYMBOLS \n";
cout << "--------------------- \n";
valid = false;
cin.clear();
cin.ignore();
}
}
}
答案 0 :(得分:2)
发生循环是因为在提取一个字符后,cin
缓冲区中仍有字符。因此,如果您键入querty<enter>
,则在处理q
之后,它仍然需要处理uerty\n
。然后循环,因为它没有找到满足条件choice > 6 || choice < 1
的输入值并尝试其他字符提取。它可以执行6次,直到缓冲区为空并且设置了cin.fail()
标志。
另一种方法是以字符串形式读取整行,并从该行中提取整数。
#include <iostream>
#include <sstream>
#include <string>
using namespace std;
int displayUserInstructions(){
string line;
while(true){
cout << "Which function would you like to use? \n";
cout << "1) Average Function \n";
cout << "2) Mean Absolute Deviation Function \n";
cout << "3) Number Sorting Function \n";
cout << "4) Median Function \n";
cout << "5) All of the above \n";
cout << "6) Calculator Function \n";
cout << "Your choice: ";
if(getline(cin, line)){
stringstream ss(line);
int choice;
if(ss >> choice && (choice >= 1 && choice <= 6)){
return choice;
}
cout << "ERROR, PLEASE ENTER ONLY VALID SYMBOLS \n";
cout << "--------------------- \n";
}
}
}
int main()
{
int choice = displayUserInstructions();
cout << "You made the valid choice of " << choice << '\n';
}
答案 1 :(得分:2)
当您输入“qwerty”时,表示输入缓冲区中有六个字符等待读取。您的代码尝试使用cin >> choice
读取整数,但发现它不是有效的整数,因此会输出错误,清除流状态,丢弃一个字符,然后重新启动循环。然后它读取下一个字符'w'
,它不是一个有效的整数,因此它会输出错误并丢弃一个字符,然后重新启动。
您可以通过将所有内容丢弃到下一个换行符来解决此问题:
cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
这会将所有字符丢弃到行尾,而不是试图从错误的输入中继续读取整数。
或者,您可以立即读取整行并尝试从中提取整数(如Paul Rooney的回答所示)。两者都应该同样有效,尽管取决于您在计划中下一步要做什么,一个或其他解决方案可能更灵活。一个解决方案读取整行然后尝试从中提取整数(并忽略该行的其余部分)。另一个解决方案尝试首先提取一个整数并在出错时丢弃该行(如果没有错误,则该行的其余部分仍然可读)。