getline вызывает бесконечный цикл при перенаправлении файла на стандартный ввод

Следующий код просто повторяет стандартный ввод на стандартный вывод. Если я запускаю программу так ./a.outЯ могу напечатать что угодно, и программа работает нормально. Однако, если я запустлю это так ./a.out < input.txt Я получаю бесконечный цикл, независимо от содержания input.txt,

#include <iostream>

using namespace std;

int main() {
string input;
while (true) {
cout << "Type your input: ";
getline(cin, input);
cout << input << endl;
}
return 0;
}

Что я делаю неправильно?

РЕДАКТИРОВАТЬ: Чтобы уточнить, я ожидаю, что после завершения ввода из входного файла, getline ждет большего ввода от stdin. Вместо этого он продолжает читать, когда ничего нет.

2

Решение

У вас нет завершающего условия для вашего цикла: while (true) это бесконечный цикл в любом случае — то есть без разрыва / выхода / и т.д. в теле цикла.

Я предполагаю, что при использовании вашей программы, чтобы эхо stdin Вы заканчиваете это нажатием Ctrl-C. Запустите вашу программу, используя ./a.outи введите Ctrl-D (EOF): вы также получите бесконечный цикл.

Посмотри на документы за getline: используйте возвращаемое значение для завершения вашего цикла:

while (getline(cin, input))
1

Другие решения

Ваш цикл не имеет условия завершения, будь то разрыв или прямо внутри while часть. Вместо этого вы, вероятно, хотите это:

while (getline(cin, input))

Это закончится, когда произойдет сбой ввода, скорее всего, в результате достижения EOF.

1

Что ты делаешь неправильно, так это то, что ты игнорировать результат операции ввода, в этом случае getline,

Вы никогда не должны игнорировать результат операции ввода. Это всегда ошибка программирования. Вы не можете знать или делать предположения о состоянии внешних данных, поэтому вы всегда должны проверять, успешно ли выполнена операция ввода. Если это не так, то это обычно ошибка доступа к предполагаемой входной переменной для чтения, так что вам действительно нужно проверять каждый раз, и до доступ к результату.

В настоящем деле std::getline возвращает ссылку на объект потока, и вы можете оценить поток как логическое значение. Это оценивает как true если и только если извлечение прошло успешно; в противном случае вы должны не использовать результат (и предположительно прекратить чтение).

В общем, код должен идти так:

for (std::string line; std::getline(std::cin, line); )
{
// use "line"}
0
По вопросам рекламы [email protected]