Нужна помощь с getline () - PullRequest
       361

Нужна помощь с getline ()

19 голосов
/ 16 ноября 2009

Есть ли причина, по которой, если в моей программе я запрашиваю ввод у пользователя, и я делаю:

int number;
string str;
int accountNumber;

cout << "Enter number:";
cin >> number;
cout << "Enter name:";
getline(cin, str);
cout << "Enter account number:";
cin >> accountNumber;

Почему после ввода первого числа выводится «Введите имя», а затем сразу же «Ввод номера счета», прежде чем я даже могу ввести свой «str» для строки getline (cin, str)? Спасибо!

Ответы [ 7 ]

21 голосов
/ 16 ноября 2009

getline(cin, str); читает символ новой строки, который следует после ранее прочитанного числа, и немедленно возвращается с этой "строкой". Чтобы избежать этого, вы можете пропустить пробел с помощью std::ws перед прочтением имени:

cout << "Enter number:";
cin >> number;
cout << "Enter name:";
ws(cin);
getline(cin, str);
...

Обратите внимание, что это также пропускает начальные пробелы после новой строки, поэтому str не будет начинаться с пробелов, даже если пользователь их вводил. Но в данном случае это, вероятно, особенность, а не ошибка ...

13 голосов
/ 16 ноября 2009

Попробуйте

cout << "Enter name:";
cin.ignore();
getline(cin, str);
5 голосов
/ 17 ноября 2009

Похоже, вы хотите читать на основе строки. Для этого вы, вероятно, захотите использовать getline последовательно, а затем проанализировать каждую строку, если вам нужно проанализировать число из прочитанной строки. Это делает входное чтение более последовательным.

Таким образом, вам не нужно вручную сканировать конец каждой строки, чтобы гарантировать, что следующая операция чтения начинается с новой строки.

Это также упрощает добавление обработки ошибок для повторяющихся запросов ввода.

, например

#include <string>
#include <iostream>
#include <istream>
#include <ostream>
#include <sstream>

int parse_integer(const std::string& input)
{
    std::istringstream iss(input);
    int result;
    if (!(iss >> result))
    {
        // error - throw something?
    }
    return result;
}

int main()
{
    int number;
    std::string str;
    int accountNumber;

    std::string inputline;

    std::cout << "Enter number: ";

    if (!std::getline(std::cin, inputline))
    {
        // error - throw something?
    }

    number = parse_integer(inputline);

    std::cout << "Enter name:";

    if (!std::getline(std::cin, inputline))
    {
        // error - throw something?
    }

    str = inputline;

    std::cout << "Enter account number:";

    if (!std::getline(std::cin, inputline))
    {
        // error - throw something?
    }

    accountNumber = parse_integer(inputline);

    return 0;
}
2 голосов
/ 16 ноября 2009

Мне кажется, проблема в том, что cin >> передает символ новой строки (\n). Getline () предполагает, что символ новой строки является пробелом и передает его дальше. Кто-то опубликовал решение, которое вы можете использовать.

Вы можете использовать манекен getline(cin, dummy); или настоящую вещь cin.ignore(100,'\n');

2 голосов
/ 16 ноября 2009
cin >> number

только захватывает числа из буфера, он оставляет «enter» в буфере, который затем сразу же захватывается getline и интерпретируется как пустая строка (или строка только с новой строкой, я забыл). 1002 *

2 голосов
/ 16 ноября 2009
cin >> number // eat the numeric characters
getline(cin, str) // eat the remaining newline
0 голосов
/ 30 января 2019

Не используйте getline(): это плохо для распределения памяти. Используйте fgets(). См. fgets ссылка .

...