在cin之后使用getline(cin,s)

时间:2011-04-21 05:29:22

标签: c++ getline cin

我需要以下程序来获取整行用户输入并将其放入字符串名称中:

cout << "Enter the number: ";
int number;
cin >> number;

cout << "Enter names: ";
string names;

getline(cin, names);

cin >> number命令之前使用getline()命令(我猜这是问题),它不允许我输入名称。为什么呢?

我听说过cin.clear()命令,但我不知道这是如何工作的,或者为什么这是必要的。

14 个答案:

答案 0 :(得分:17)

cout << "Enter the number: ";
int number;
cin >> number;

cin.ignore(256, '\n'); // remaining input characters up to the next newline character
                       // are ignored

cout << "Enter names: ";
string names;
getline(cin, names);

答案 1 :(得分:15)

另一种方法是放一个

cin.ignore ( std::numeric_limits<std::streamsize>::max(), '\n' ); 

cin>>number;完全刷新输入缓冲区之后(拒绝所有额外字符,直到找到换行符)。您需要#include <limits>才能获得max()方法。

答案 2 :(得分:9)

cout << "Enter the number: ";
int number;
if (cin >> number)
{
    // throw away the rest of the line 
    char c;
    while (cin.get(c) && c != '\n')
        if (!std::isspace(c))
        {
            std::cerr << "ERROR unexpected character '" << c << "' found\n";
            exit(EXIT_FAILURE);
        }
    cout << "Enter names: ";
    string name;
    // keep getting lines until EOF (or "bad" e.g. error reading redirected file)...
    while (getline(cin, name))
        ...use name...
}
else
{
    std::cerr << "ERROR reading number\n";
    exit(EXIT_FAILURE);
}

在上面的代码中,这一位......

    char c;
    while (cin.get(c) && c != '\n')
        if (!std::isspace(c))
        {
            std::cerr << "ERROR unexpected character '" << c << "' found\n";
            exit(EXIT_FAILURE);
        }

...在数字只包含空格后检查输入行的其余部分。

为什么不使用ignore?

这非常详细,因此在ignore之后在流上使用>> x是一种经常推荐的替代方法,可以将内容丢弃到下一个换行符,但它可能会丢弃非空白内容这样做,可以忽略文件中的损坏数据。您可能会也可能不会关心,具体取决于文件内容是否可信,避免处理损坏数据的重要性等。

那么你什么时候使用clear并忽略?

因此,std::cin.clear()(和std::cin.igore())不是必需的,但对于删除错误状态很有用。例如,如果您想给用户很多机会输入有效数字。

int x;
while (std::cout << "Enter a number: " &&
       !(std::cin >> x))
{
    if (std::cin.eof())
    {
        std::cerr << "ERROR unexpected EOF\n";
        exit(EXIT_FAILURE);
    }

    std::cin.clear();  // clear bad/fail/eof flags

    // have to ignore non-numeric character that caused cin >> x to
    // fail or there's no chance of it working next time; for "cin" it's
    // common to remove the entire suspect line and re-prompt the user for
    // input.
    std::cin.ignore(std::numeric_limits<std::streamsize>::max());
}

使用skipws或类似的东西不是更简单吗?

对于原始要求,ignore的另一个简单但半成品的替代方法是在阅读行之前使用std::skipws跳过任意数量的空格...

if (std::cin >> number >> std::skipws)
{
    while (getline(std::cin, name))
        ...

...但是如果输入像“1E6”(例如某些科学家试图输入1,000,000但C ++只支持浮点数的符号)将不接受,那么你最终会得到{{1}设置为number1读取为E6的第一个值。另外,如果您有一个有效数字后跟一个或多个空行,那么这些行将被默默忽略。

答案 3 :(得分:9)

尝试:

int number;

cin >> number;

char firstCharacterOfNames;
cin >> firstCharacterOfNames;  // This will discard all leading white space.
                               // including new-line if there happen to be any.

cin.unget();                   // Put back the first character of the name.

std::string  names;
std::getline(cin, names);      // Read the names;

可替换地。如果您知道数字和名称将始终位于不同的行上。

cin >> number;
cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n'); 
std::getline(cin, names);

答案 4 :(得分:5)

在使用getline之前,您可以使用std :: ws在输入缓冲区中提取任何空白字符。 std :: ws的标题是sstream。

cout << "Enter the number: ";
int number;
cin >> number;
cout << "Enter names: ";
string names;
cin>>ws;
getline(cin, names);

答案 5 :(得分:1)

或者您可以刷新输入缓冲区以读取字符串

  

fflush(标准输入)

它在头文件 stdio.h 中定义。

此代码有效..

cout << "Enter the number: ";
int number;
cin >> number;

cout << "Enter names: ";
string names;
fflush(stdin);  //FLUSHING STDIN
getline(cin, names);

答案 6 :(得分:1)

cout << "Enter the number: ";
int number;
cin >> number;

cout << "Enter names: ";
string names;
getline(cin, names);//works on the \n left behind
getline(cin, names);//continues and rewrites names

它非常自我解释,在cin >> number使用的流中有一个\ n,它在第一次使用时被分配给名称。重用getline会立即写入正确的值。

答案 7 :(得分:0)

您可以在cppreference找到所需的答案。

  

在以空格分隔的输入后立即使用,例如在int n; std::cin >> n;之后,getline会使用运算符&gt;&gt;消耗输入流上留下的结束字符,并立即返回。一个常见的解决方案是在切换到面向行的输入之前忽略输入行上的所有剩余字符cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');

答案 8 :(得分:0)

你想在你的cin语句之后使用cin.ignore(),因为你想在使用cin获取你的int变量之后忽略缓冲区中的“\ n”。

我有一个类似的程序我用过类似的问题:

  creationmonth MonthCreated    TotalCount  NewCount    RetreivedON

  8             August          11238       1629        8/1/2016 0:00

  9             September       12310       721         9/1/2016 0:00

答案 9 :(得分:0)

我刚用过

getline(cin >> ws,lard.i_npute);

标准

#include <iostream>

在我遇到回车问题和ws操纵器工作的情况下的标题。我可能会开始将循环函数作为类嵌入并使用构造函数和析构函数调用atleast。

答案 10 :(得分:0)

从概念上讲,我认为你希望每个答案都整齐排成一行。那么你为什么不尝试这个呢?

cout << "Enter the number: ";
string line;
getline(cin, line);
int number = std::stoi(line);

cout << "Enter names: ";
string names;
getline(cin, names);

代码正确使用第一个换行符,如果行正确则给出数字,否则抛出异常。一切都是免费的!

答案 11 :(得分:0)

在getline()函数之前使用cin时,请尝试cin.ignore()

void inputstu(){
    cout << "Enter roll Number:";
    cin >> roll_no;
    cin.ignore(); //ignore the withspace and enter key
    cout << "Enter name:";
    getline(cin, stu_name);
}

答案 12 :(得分:0)

cout << "Enter the number: ";

int number;
cin >> number;

getc(stdin);  //you need add this line 

cout << "Enter names: ";

string names;

getline(cin, names);

答案 13 :(得分:-1)

#include <iostream>
#include <string>

using namespace std;

int main()
{
    cout << "Enter the number: ";
    int number;
    cin >> number;
    cout << "Enter names: ";
    string names;

    // USE peek() TO SOLVE IT! ;)
    if (cin.peek() == '\n') {
        cin.ignore(1 /*numeric_limits<streamsize>::max()*/, '\n');
    }

    getline(cin, names);

    return 0;
}

使用cin.peek()向前看,看看'\n'的内部缓冲区中是否还有cin。如果是这样:忽略它(基本上跳过它)