Почему getline не работает после cin c
Перейти к содержимому

Почему getline не работает после cin c

  • автор:

getline в C++: чтение строки

Привет! В этой статье мы поговорим о функции std::getline из стандартной библиотеки C++. Эта функция позволяет нам прочитать строку из любого потока ввода.

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

Иллюстрация getline в C++

Чтение строки из потока при помощи getline

getline является частью заголовочного файла . У этой функции есть два варианта:

istream& getline (istream& is, string& str); istream& getline (istream& is, string& str, char delim);

Эта функция читает поток is до тех пор, пока не встретит разделительный символ. По умолчанию, это символ переноса строки \n , но мы можем указать любой другой передав delim .

Сохраняет прочитанное getline в аргумент str типа std::string , который мы передаем ей в качестве второго аргумента. Все, что хранилось в строке, будет перезаписано прочитанным из потока ввода is .

Возвращает функция поток, из которого была прочитана строка: первый параметр is .

Давайте посмотрим на пример использования функции getline :

#include using namespace std; int main()  string input; getline(cin, input); cout  <"input = \""   <"\""  ; return 0; > 
чтение до конца строки input = "чтение до конца строки"

В этом простом примере мы прочитали из стандартного ввода первую строку. В данном случае это «чтение до конца строки» .

Мы также можем поменять символ, до которого мы хотим читать строку:

#include using namespace std; int main()  string input; getline(cin, input, ';'); cout  <"input = \""   <"\""  ; return 0; >
первая часть; вторая часть input = "первая часть"

Тут мы добавили третий аргумент — ‘;’ . Поэтому мы получили только то, что было до точки с запятой.

Мы также можем прочитать несколько строк одним вызовом getline :

первая часть; input = "первая часть"

Тут getline продолжил чтение, даже после того, как первая строка закончилась, и началась вторая.

В каком случае следующая программа выведет строку “Прочитано успешно”?

#include #include #include using namespace std; int main()  string input; ifstream file("text.txt"); getline(file, input, '*'); if(input == "test") cout  <"Прочитано успешно"  ; else cout  <"Ошибка чтения"  ; return 0; >

Предполагаем, что файл text.txt существует и может быть прочитан. Каким содержимым должен обладать text.txt ?

test*продолжение файла

getline в данном случае читает из файла до тех пор, пока не встретит символ * . Для того чтобы условие if(input == «test») было истинным, строка перед символом * должна быть именно «test» .

В примерах выше мы считывали строку из стандартного ввода. Однако getline позволяет нам читать с любого потока. Давайте теперь попробуем считать строку из файла.

Чтение из файла при помощи getline

Поскольку getline может читать из любого потока ввода, давайте воспользуемся классом ifstream для чтения из файла:

#include #include using namespace std; int main()  ifstream shows_file("shows.txt"); string show; getline(shows_file, show); cout  <"show = \""   <"\""  ; return 0; >
Rick and Morty Stranger Things Game of Thrones
show = "Rick and Morty"

В программе выше мы поменяли первый аргумент функции getline с cin (поток стандартного ввода) на shows_file (поток ввода из файла).

Использование цикла while с getline

Зачем нам останавливаться на первом шоу? Давайте прочитаем все строки, которые есть в файле shows.txt. Для этого можно воспользоваться циклом while :

#include #include using namespace std; int main()  ifstream shows_file("shows.txt"); string show; while (getline(shows_file, show))  cout  <"show = \""   <"\""  ; > return 0; >
Rick and Morty Stranger Things Game of Thrones 
show = "Rick and Morty" show = "Stranger Things" show = "Game of Thrones"

Как вы можете видеть, для чтения всего файла достаточно использовать возвращаемое значение getline в условии цикла while . Так можно сделать, потому что в ifstream реализован оператор конвертации в bool .

При конвертации в bool , ifstream возвращает true если можно продолжить чтение, false если нельзя:

cout  "can read: "  (bool)shows_file  endl; while (getline(shows_file, show))  cout  "show = \""  show  "\""  endl; > cout  "can read: "  (bool)shows_file  endl;

Тут мы только добавили конвертацию в bool до и после цикла. Вывод программы:

can read: 1 show = "Rick and Morty" show = "Stranger Things" show = "Game of Thrones" can read: 0

Ожидаемо, мы не можем продолжить чтение после “Game of Thrones” (в файле после этого больше ничего нет).

Ошибки при работе с getline

При работе с потоками ввода всегда могут произойти ошибки. Для того, чтобы понять, что произошло, можно воспользоваться флагами на потоке ввода:

  1. stream.good() : возвращает true если все прошло без ошибок.
  2. stream.eof() : поток ввода

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *