如何摆脱坏输入一次一个字,而不是一次一行? [英] How to get rid of bad input one word at a time instead of one line at a time?
问题描述
我在阅读C ++ primer plus / Stephen Prata
I am reading "C++ primer plus/Stephen Prata"
这是本书的代码
while (!(cin >> golf[i])) {
cin.clear(); // reset input
while (cin.get() != '\n')
continue; // get rid of bad input
cout << "Please enter a number: ";
}
上述代码很容易理解。
但是这本书的上下文提到了
But the context from this book mentions
程序在while循环中使用cin.get()来读取剩余的输入通过结束行。这除去了坏的输入,以及任何其他的行上
另一种方法是读取到下一个空白,它摆脱了坏的输入一个字在一个
最后,程序会告诉用户输入一个数字。
"...the program uses cin.get() in a while loop to read the remaining input through the end of the line.This gets rid of the bad input, along with anything else on the line. Another approach is to read to the next whitespace, which gets rid of bad input one word at a time instead of one line at a time. Finally, the program tells the user to enter a number."
我不知道另一个方法是?
I wonder what the another approach is?
我尝试以不同的方式表示代码,我知道它不正确。
I try to express the code in different way and I know it's not correct.
while (!(cin >> golf[i])) {
cin.clear(); // resset input
char word[20];
while (cin >> word)
continue; // get rid of bad input
cout << "Please enter a number: ";
}
如何编码读取到下一个空格,
How do I code to read to the next whitespace, which gets rid of bad input one word at a time instead of one line at a time?
感谢您的阅读。
推荐答案
让我们先看看现有的代码:
Let's start by looking at the existing code:
while (cin.get() != '\n')
continue;
这是读到新行的内容。我们读一个字符,比较它与新行,如果不相等,我们读另一个字符。因此,它读取字符,并在它到达一个新行时停止读取。
This is what reads up to the new-line. We read a character, compare it to the new-line, and if it's not equal, we read another character. So, it reads characters, and stops reading when it gets to a new-line.
如果我们想读取一个空格字符,我们只是更改值比较:
If we want to read to a space character instead, we just change the value we compare to:
while (cin.get() != ' ')
continue;
如果我们要停止在任何使用函数告诉我们一个字符是否是空格。该函数看起来像这样:
If we want to stop reading at any white-space, we could use a function to tell us whether a character is white space or not. That function would look something like this:
bool is_white_space(char ch) {
return ch == ' ' || ch == '\t' || ch == '\n' || ch == '\r' || ch == '\v';
}
但这是一个常见的任务,标准库已经有一个 isspace
函数,所以我们不必自己写。我们只需要使用它:
But this is a common enough task that the standard library already has an isspace
function, so we don't have to write our own. We just have to use it:
while (!isspace(cin.get())
continue;
就我个人而言,我至少考虑把它放入一个函数本身, skip_to_whitespace
,所以我们的外循环看起来像:
Personally, I'd at least consider putting this into a function by itself, and giving it a readable name like skip_to_whitespace
, so our outer loop would look something like:
void skip_to_space(std::istream &in) {
in.clear();
while (!isspace(in.get()))
continue;
}
// ...
while (!(cin >> golf[i])) {
skip_to_space(cin);
cout << "Please enter a number: ";
}
至少对我来说,代码的意图显然更加明显 - 我们不必通读循环的内容,弄清楚它应该做什么 - 这从函数的名称显而易见。
At least to me, this seems to make the intent of the code considerably more apparent--we don't have to read through the content of the loop to figure out what it's supposed to do--that's obvious from the name of the function.
有一个最后一件事我会改变。 while
循环通常应该没有效果,如果其条件为假。然而,这一个,总是从其输入中读取至少一个字符,而不管该字符可能是什么。为了使这个事实更加明显,我更喜欢使用 do
循环,以正确反映循环总是至少执行一次的意图:
There is one last thing I'd change though. A while
loop should normally have no effect if its condition is false. This one, however, always reads at least one character from its input, regardless of what that character might be. To make that fact more apparent, I'd prefer to use a do
loop, to correctly reflect the intent that the loop always executes at least once:
void skip_to_space(std::istream &in) {
in.clear();
char ch;
do {
ch = in.get();
} while (!isspace(ch));
}
现在很明显, cin.get
总是发生至少一次,并且继续发生,直到我们到达一个空格字符。
Now it's obvious that the cin.get()
always happens at least once, and continues to happen until we reach a white-space character.
这篇关于如何摆脱坏输入一次一个字,而不是一次一行?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!