Ignore c что это
Добрый день. Читаю книгу, имеется такой вот код:
#include using namespace std; int main() < int num = 0; while(true) < cout > num; if(cin.good()) < cin.ignore(10, '\n'); break; >cin.clear(); cout cout
Запрашиваем число и проверяем, чтобы оно было числом, а не символом. Но не все тут понимаю.
Почитал про cin.ignore(). Написано, что он считывает до 10 символов, либо до ‘\n’ и исключает их из потока. Я не понимаю, что означает «исключает из потока». Ведь если выполняется cin.good(), то в моем понимании число исключается из потока и в поток ничего передаваться не должно (ведь значение было исключено). Тем не менее на выходе из программы мы получаем наше число. Помогите, пожалуйста, разобраться.
Последний раз редактировалось Dima-War; 13.07.2013 в 08:49 .
Регистрация: 28.01.2009
Сообщений: 20,999
cin.good() лишь проверяет состояние флагов, и ничего не делает с входным буфером.
Хорошо поставленный вопрос это уже половина ответа. | Каков вопрос, таков ответ.
Программа делает то что написал программист, а не то что он хотел.
Функции/утилиты ждут в параметрах то что им надо, а не то что вы хотите.
| Пепел Феникса |
| Посмотреть профиль |
| Найти ещё сообщения от Пепел Феникса |
Форумчанин
Регистрация: 17.03.2012
Сообщений: 105
Нет, я понимаю. Просто когда выполняется условие, то по идее cin.ignore() исключает введенное число из потока. Так почему тогда мы получаем его на выходе из программы?
Регистрация: 28.01.2009
Сообщений: 20,999
число сначала считывается, и лишь потом исключается то что осталось в потоке.
Хорошо поставленный вопрос это уже половина ответа. | Каков вопрос, таков ответ.
Программа делает то что написал программист, а не то что он хотел.
Функции/утилиты ждут в параметрах то что им надо, а не то что вы хотите.
| Пепел Феникса |
| Посмотреть профиль |
| Найти ещё сообщения от Пепел Феникса |
Форумчанин
Регистрация: 17.03.2012
Сообщений: 105
Ок, тогда зачем в условии мы используем cin.ignore()? Ведь по большому счету оно нам ничего не дает. Или я не прав?
Регистрация: 28.01.2009
Сообщений: 20,999
Сообщение от Dima-War
Ок, тогда зачем в условии мы используем cin.ignore()? Ведь по большому счету оно нам ничего не дает. Или я не прав?
в условии её нет.
а если вы имеете в виду истиную ветку ифа, то там она чистит буфер за собой, от лишних символов ввода и самого символа переноса строки(а то с ним бывает морока)
Хорошо поставленный вопрос это уже половина ответа. | Каков вопрос, таков ответ.
Программа делает то что написал программист, а не то что он хотел.
Функции/утилиты ждут в параметрах то что им надо, а не то что вы хотите.
| Пепел Феникса |
| Посмотреть профиль |
| Найти ещё сообщения от Пепел Феникса |
Форумчанин
Регистрация: 17.03.2012
Сообщений: 105
Сообщение от Пепел Феникса
в условии её нет.
а если вы имеете в виду истиную ветку ифа, то там она чистит буфер за собой, от лишних символов ввода и самого символа переноса строки(а то с ним бывает морока)
Имел ввиду ветку ифа. Все понял, спасибо.
Проблема с cin.ignore()
Что-то непонятно — вы вызываете cin.ignore() которая выбрасывает первый символ строки, и пишете что это проблема. Вы чего-то другого от этой функции ожидали?
7 мар 2019 в 21:50
Я и сам понял что что-то не так, ответ «А что вы ожидали?» не очень то и помог
7 мар 2019 в 22:16
2 ответа 2
Сортировка: Сброс на вариант по умолчанию
Както допер сам
int main() < system("chcp 1251>null"); srand(time(NULL)); text txt; char word[256]; cout > txt.linesCount; char f[1]; for (int i = 0; i < txt.linesCount; ++i) < cout > word; strcat(txt.lines[i], word); strcat(txt.lines[i], " "); > while (cin.get() != '\n'); > >
Отслеживать
ответ дан 7 мар 2019 в 22:14
Виталий Мороз Виталий Мороз
Ваше решение — читать по словам — несколько, гм. непрямое.
Вот чтение строки, если уж так нужно именно в массив: cin.getline(word,256);
Вот полный код (убрал вашу структуру, чтоб скомпилировать. думаю, вернуть назад не проблема? :)) ignore() надо один раз — после чтения количества строк.
int linesCount; char word[256]; cout > linesCount).ignore(std::numeric_limits::max(), '\n'); for (int i = 0; i < linesCount; ++i) < cout Отслеживать ответ дан 8 мар 2019 в 6:37 218k 15 15 золотых знаков 117 117 серебряных знаков 229 229 бронзовых знаков
-
Важное на Мете
Похожие
Подписаться на ленту
Лента вопросаДля подписки на ленту скопируйте и вставьте эту ссылку в вашу программу для чтения RSS.
Дизайн сайта / логотип © 2023 Stack Exchange Inc; пользовательские материалы лицензированы в соответствии с CC BY-SA . rev 2023.10.27.43697
Нажимая «Принять все файлы cookie» вы соглашаетесь, что Stack Exchange может хранить файлы cookie на вашем устройстве и раскрывать информацию в соответствии с нашей Политикой в отношении файлов cookie.
Что делает cin.ignore();

Как работает cin.peek, cin,get, cin.ignore, cin.clear?
Здравствуйте, товарищи и не товарищи!:) Я только начал изучать C++, а уже использую вещи, которые.
Метод getline(cin, m) не срабатывает без cin.ignore() / Ревью кода
Почему в моем случае getline(cin, m) не срабатывает без cin.ignore() ? Если по коду есть.

Объясните работу методов cin.getline и cin.ignore
Фрагмент программы ниже. Что делают cin.getline и cin.ignore (12-13 строки) void.
Если без параметров, то удаляет один символ из потока. В данном случае '\n', который остаётся после ввода number.
Регистрация: 23.08.2015 Сообщений: 458 Т.е. всё что будет введено после number не будет напечатано так? Регистрация: 28.07.2016 Сообщений: 41 cin.ignore() Игнорирует син. Регистрация: 23.08.2015 Сообщений: 458 Не понял честно говоря Регистрация: 11.05.2016 Сообщений: 113 Maxim09, cin.ignore () — функция, которая считывает символ и игнорирует его Регистрация: 28.07.2016 Сообщений: 41А что непонятно? cin.ignore() убирает новую строку из син.
Добавлено через 39 секунд
Сообщение от fire_Rising 
Я поставил // перед этим cin.ignore () и ничего не изменилось. Объясните мне как оно работает!
Добавлено через 2 минуты
Разве что прога стала вылетать сразу после ввода без system( "pause" );
1 2 3 4 5 6 7 8
char stroka[100] = "***"; int n = 5; cin >> n; // символ новая строка '\n' осталась в син. cin.getline(stroka, 100); // что читается? правильно, что осталось в син, т.е. '\n' cout n endl; cout stroka;
Регистрация: 23.08.2015
Сообщений: 458
Или я дурак или лыжи не едут
Так и не понял ведь вроде ничего не меняется в проге!
и с
cin.ignore()
работает и без него т.е. в компиляторе он скидывает на новую строку и с cin.ignore() и без него я в тупиковой ситуации! Да и ко всему прочему некоторые говорят что cin.ignore() игнорирует cin а некоторые что '\n' как тут разобраться
Регистрация: 28.07.2016
Сообщений: 41
да там просто. во смотри когда сначала читается число а потом строка вот тогда начнутся глюки. потому что после ввода числа символ новой строки остается в син. а когда начинается считывание строки вот тогда программа читает '\n' и думает что ввод закончен
Добавлено через 2 минуты
ну теперь то хоть понятно
Регистрация: 23.08.2015
Сообщений: 458
Добавлено через 20 секунд
И смех и грех.
Регистрация: 28.07.2016
Сообщений: 41
син.игноре() читает символы из входного потока до '\n'
7595 / 6418 / 2924
Регистрация: 14.04.2014
Сообщений: 27,947
TheBig, не до '\n', а до EOF.
Maxim09, когда ты вводишь, например 10, в потоке будет "10\n". В number попадут только цифры, а '\n' останется в потоке и, возможно, будет мешать другим операциям ввода. Поэтому его удаляют.
Регистрация: 28.07.2016
Сообщений: 41
nmcf, до '\n' это конец строки
7595 / 6418 / 2924
Регистрация: 14.04.2014
Сообщений: 27,947
TheBig, с документацией ознакомься. По умолчанию до EOF.
Регистрация: 28.07.2016
Сообщений: 41
ну вообще то да, до EOF. тут я согласен
Регистрация: 23.08.2015
Сообщений: 458
Наткнулся вот на такое если вас не затруднит то напишите по это ШТУКЕ прогу да я посмотрю!
Ну например:
Твоя программа запросила: Введите количество студентов.
Юзер ввел: 3
Программа просит: А теперь введите оценки этих студентов.
Юзер вводит оценки для первого студента, для второго, для третьего, для четвертого, для пятого.
Вот в этом случае оценки для первых трех ты читаешь, а дальнейший ввод игнорируешь.
cin.get() и его друзья
определенная в классе istream библиотеки по определению извлекает из входного потока один символ и возвращает его целочисленный код. Популярность ей принес тот факт, что ее удобно использовать в программах с консольным интерфейсом, которые запускаются не из консоли, например, из проводника или из графического интерфейса IDE. После завершения работы программы мы не сможем увидеть ее финальный вывод, поскольку выполнится инструкция return и программа завершится, закрывая «за собой» консольное окно.
Функция get() же стандартного потока ввода cin заставляет систему ожидать ввода пользователем любого символа, который она считывает, и программа завершается.
Проблема в том, что работает cin.get() далеко не всегда. Почему? Рассмотрим ситуацию издалека.
Начнем с того, что же такое поток (stream). Ненаучным языком говоря, поток — последовательность символов. Источником символов может служить в частности клавиатура. Символы идут один за другим:
К ним возможен только последовательный доступ, но не произвольный, иными словами, чтобы извлечь из потока символ d , надо предварительно извлечь из него a , b и c . Извлеченный (прочитанный) символ удаляется из потока.
Надо сказать, что если по каким-то причинам из потока прочитаны не все символы до конца строки (символа '\n' ) включительно, то после операции чтения поток не будет пустым. Два самых распространенных способа дают нам два хороших примера.
Уже рассматривавшаяся выше функция get() читает из потока один символ, так что если мы ввели несколько символов, то она оставит за собой непустой поток. И следующий вызов cin.get() будет обречен на «фиаско»: программа вместо того, чтобы остановиться и ждать пользовательского ввода, прочитает из входного потока очередной символ, оставшийся от предыдущего ввода, и продолжит свое выполнение. Или завершится «без спроса». Напомню, что get() возвращает приведенный к типу int код введенного символа, поэтому мы может использовать его в вышеприведенной инструкции — код просто будет выведен на экран.
Собственно вывод: если в конце программы cin.get() не ждет пользовательского ввода, значит, вы оставили за собой непустой входной поток.
2)
int a;
cin>>a;
Перегруженный оператор сдвига, использующийся для ввода данных из потока, который в свою очередь перегружен для работы с целыми числами (так как вызван с параметром a типа int ), считывает символы, являющиеся десятичными цифрами, до тех пор, пока не встретит нецифровой символ. Это может быть пробел, буква, табуляция, конец строки, и так далее.
Все эти символы остались в потоке. Даже если вы просто ввели число и нажали Enter, символ '\n' остался в потоке.
На него и «нарывается» впоследствии cin.get() .
Следующая шуточная программка позволяет воочию увидеть «обидчика». Скомпилируйте ее, запустите и введите, к примеру,
Она выведет символ, на котором «споткнулся» cin.get() .
using namespace std;
Теперь, когда проблема очевидна, рассмотрим ее возможные решения. В порядке увеличения их сложности.
1)
Функция
определенная в классе istream , извлекает из потока символы и отбрасывает их. Причем она так поступает либо с n символами, либо со всеми символами, пока в потоке не встретится символ, заданный параметром delim .
В нашем случае мы стремимся отбросить максимальное число символов, которое может содержать поток, до первого перевода строки включительно.
2)
streambuf* istream::rdbuf() const;
streamsize streambuf::in_avail();
У потока ввода есть буфер чтения, в котором он хранит символы. Мы обращаемся к нему, вызывая функцию rdbuf() . А любой уважающий себя буфер знает, сколько символов в нем содержится. Поскольку и мы хотим это узнать, мы вызываем функцию in_avail() этого буфера. Это количество символов нам и нужно проигнорировать, что достигается так:
cin.ignore(cin.rdbuf()->in_avail());
Второй параметр функции ignore() имеет значение по умолчанию, что делает его необязательным, и мы его просто опускаем при вызове.
3)
int istream::sync();
Использование функции sync() — путь наименьшего сопротивления. Она просто очищает поток от имеющихся в нем символов.
Почему этот способ самый сложный — поищите в Гугле (если есть желание). А я в это время порекомендую Вам выбрать более понравившийся из первых двух и пойду заниматься более полезными делами
Хотя нет, напоследок еще расскажу о функции
void ios::clear(iostate state = goodbit);
Эта функция восстанавливает поток, если он по какой-либо причине оказался в ошибочном состоянии. Например, из потока пытались прочитать число, а там в это время находились буквы. В этом случае, поток переводится в состояние отказа, и дальнейшие операции с ним неосуществимы. В том числе и cin.get() . Функция же clear() «очищает» состояние потока, делая его вновь веселым и работоспособным.
На закуску пример и ссылки.