如何一次删除一个单词的错误输入而不是一次一行?

时间:2015-02-20 14:39:18

标签: c++

我正在阅读" 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: ";
    }

上面的代码很容易理解。

但是本书的背景提到了

&#34; ...程序在while循环中使用cin.get()来读取通过行尾的剩余输入。这消除了错误的输入以及行上的任何其他内容。 另一种方法是读取下一个空格,一次删除一个字的错误输入,而不是一次删除一行。 最后,程序告诉用户输入一个数字。&#34;

我想知道另一种方法是什么?

我尝试以不同的方式表达代码,我知道它不正确。

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

如何编写代码来读取下一个空格,一次删除一个单词的错误输入,而不是一次删除一行?

谢谢你的阅读。

2 个答案:

答案 0 :(得分:3)

让我们从查看现有代码开始:

    while (cin.get() != '\n')
        continue;

这是读取新行的内容。我们读了一个字符,将它与新行进行比较,如果它不相等,我们会读另一个字符。因此,它会读取字符,并在到达换行符时停止读取。

如果我们想要读取空格字符,我们只需将我们比较的值更改为:

    while (cin.get() != ' ')
        continue;

如果我们想停止在任何空白区域阅读,我们可以使用一个函数来告诉我们角色是否是空格。该功能看起来像这样:

bool is_white_space(char ch) { 
    return ch == ' ' || ch == '\t' || ch == '\n' || ch == '\r' || ch == '\v';
}

但这是一项非常普遍的任务,标准库已经具有isspace功能,因此我们不必编写自己的功能。我们只需要使用它:

while (!isspace(cin.get())
    continue;

就个人而言,我至少考虑将它自己放入一个函数中,并赋予它一个可读的名称,如skip_to_whitespace,所以我们的外部循环看起来像:

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

至少对我而言,这似乎使代码的意图更加明显 - 我们不必阅读循环内容以弄清楚它应该做什么 - - 从功能名称中可以看出这一点。

我最后还有一件事要改变。如果条件为false,则while循环通常不起作用。但是,这一个始终从其输入中读取至少一个字符,而不管该字符可能是什么。为了使这一事实更加明显,我更倾向于使用do循环来正确反映循环总是至少执行一次的意图:

void skip_to_space(std::istream &in) { 
    in.clear();
    char ch;

    do {
        ch = in.get();
    } while (!isspace(ch));
}

现在显而易见的是,cin.get()总是至少发生一次,并且一直发生,直到我们达到白色空间角色。

答案 1 :(得分:0)

要丢弃字词,直到找到一个数字:

string word;

cout << "Please enter a number: ";

while(!(cin >> golf[i])){
    cin.clear();
    cin >> word;

    if(cin.rdbuf()->in_avail() == 1){
        cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
        cout << "Please enter a number: ";
    }
}

抛弃整行的一种方法是使用ignore

while (!(cin >> golf[i])) {
    cin.clear();    // resset input
    cin.ignore(numeric_limits<streamsize>::max(), '\n');   // get rid of bad input
    cout << "Please enter a number: ";
}