while(cin) как выйти из данного цикла
Разбираю калькулятор из книги Страуструпа, лексемы вроде как считывает правильно, но не могу понять как выйти из цикла. Если ввожу ctrl + z выдаёт ошибку.
using namespace std; class Token < public: char kind; // what kind of token double value; // for numbers: a value Token(char ch) // make a Token from a char :kind(ch), value(0) < >Token(char ch, double val) // make a Token from a char and a double :kind(ch), value(val) < >>; //------------------------------------------------------------------------------ Token get_token() // read a token from cin < char ch; cin >> ch; // note that >> skips whitespace (space, newline, tab, etc.) switch (ch) < //not yet case ';': // for "print" //not yet case 'q': // for "quit" case '(': case ')': case '+': case '-': case '*': case '/': return Token(ch); // let each character represent itself case '.': case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': < cin.putback(ch); // put digit back into the input stream double val; cin >> val; // read a floating-point number return Token('8', val); // let '8' represent "a number" > default: error("Bad token"); > > vector tok; int main() < while (cin) < Token t = get_token(); tok.push_back(t); //cout for (int i = 0; i > return 0; >
Отслеживать
задан 5 мар 2018 в 17:53
96 1 1 серебряный знак 6 6 бронзовых знаков
где тут цикл.
5 мар 2018 в 18:11
@ARHovsepyan while (cin) < Token t = get_token(); tok.push_back(t); //cout
5 мар 2018 в 18:14
да, почему то я сначала не увидел main()
5 мар 2018 в 18:37
ну там наверное по символу 'q' нужно сделать cin не валидным
5 мар 2018 в 18:42
типа std::basic_ios::setstate cin.setstate(std::ios_base::failbit) и while(cin) дальше не пойдёт
5 мар 2018 в 18:46
2 ответа 2
Сортировка: Сброс на вариант по умолчанию
Неохота расписать ошибки, просто смотрите внимательно и сравните
using namespace std; //тут лучше определить конструктор по умолчанию тоже class Token < public: char kind; // what kind of token double value; // for numbers: a value Token(char ch = ' ') // здесь. // make a Token from a char :kind(ch), value(0) < >Token(char ch, double val) // make a Token from a char and a double :kind(ch), value(val) < >>; //------------------------------------------------------------------------------ Token get_token() // read a token from cin < Token t; char ch; cin >> ch; // note that >> skips whitespace (space, newline, tab, etc.) switch (ch) < //not yet case ';': // for "print" //not yet case 'q': // for "quit" case '=': case '(': case ')': case '+': case '-': case '*': case '/': return Token(ch); // let each character represent itself case '.': case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': < cin.putback(ch); // put digit back into the input stream double val; cin >> val; // read a floating-point number return Token('8', val); // let '8' represent "a number" > default: cerr return Token(ch); > int main() < vectortok; while (cin ) < Token t = get_token(); tok.push_back(t); //из цикла выходить нужно вводя EOF (у меня это ctrl + z ) // if (t.kind == '=') break; >for (size_t i = 0; i > return 0; >
- из цикла нужно выходить вводя символ EOF(конец ввода): в моей системе это ctrl+z. Из цикла можно выходить также определив удобный для себя символ — например символ ‘=’ что я и написал в цикле как комментарий
Отслеживать
ответ дан 5 мар 2018 в 20:02
AR Hovsepyan AR Hovsepyan
15.9k 3 3 золотых знака 13 13 серебряных знаков 30 30 бронзовых знаков
Кстати да, можно было вообще просто по определённому kind break делать, чё-то меня опять не в ту степь понесло =)
5 мар 2018 в 20:37
а ошибку у него выдавало потому что там в switch по дефолту вызывается error(«Bad token»). Или нет ?
5 мар 2018 в 20:39
@vegorov, да нужно там добавить символ конца ввода конечно, но можно просто ничего не добавлять, EOF закроет цикл
5 мар 2018 в 20:45
ну мне кстати кажется что EOF это только один из вариантов. А если нужно будет несколько выражений подряд вычислять? Тут наверное правильнее добавлять обработку некоторых символов как управляющую инструкцию (попытаться вычислить последнее введёное выражение и начать ввод нового выражения/закончить ввод выражений)
While cin c как закончить ввод
Циклы позволяют выполняет некоторый набор инструкций множество раз, пока соблюдается определенное условие. В языке C++ имеются следующие виды циклов:
Цикл while
Цикл while выполняет некоторый код, пока его условие истинно, то есть возвращает true. Он имеет следующее формальное определение:
while(условие) < // выполняемые действия >
После ключевого слова while в скобках идет условное выражение, которое возвращает true или false. Затем в фигурных скобках идет набор инструкций, которые составляют тело цикла. И пока условие возвращает true, будут выполняться инструкции в теле цикла.
Например, выведем квадраты чисел от 1 до 9:
#include int main() < int i ; while(i < 10) < std::cout 1 * 1 = 1 2 * 2 = 4 3 * 3 = 9 4 * 4 = 16 5 * 5 = 25 6 * 6 = 36 7 * 7 = 49 8 * 8 = 64 9 * 9 = 81
Каждый отдельный проход цикла называется итерацией. То есть в примере выше было 9 итераций.
Если цикл содержит одну инструкцию, то фигурные скобки можно опустить:
int i <>; while(++i < 10) std::cout for (инициализатор; условие; итерация) < // тело цикла >
- инициализатор выполняется один раз при начале выполнения цикла и представляет установку начальных условий, как правило, это инициализация счетчиков - специальных переменных, которые используются для контроля за циклом.
- условие представляет условие, при соблюдении которого выполняется цикл. Как правило, в качестве условия используется операция сравнения, и если она возвращает ненулевое значение (то есть условие истинно), то выполняется тело цикла, а затем выполняется итерация .
- итерация выполняется после каждого завершения блока цикла и задает изменение параметров цикла. Обычно здесь происходит увеличение счетчиков цикла.
Например, перепишем программу по выводу квадратов чисел с помощью цикла for:
#include int main() < for(int i ; i < 10; i++) < std::cout 1 * 1 = 1 2 * 2 = 4 3 * 3 = 9 4 * 4 = 16 5 * 5 = 25 6 * 6 = 36 7 * 7 = 49 8 * 8 = 64 9 * 9 = 81
Необязательно указывать все три выражения в определении цикла, мы можем одно или даже все из них опустить:
int i ; for(; i < 10;) < std::cout #include int main() < int sum <>; for (unsigned i <>; i < 6; sum += i++); std::cout
Здесь для хранения суммы чисел определена переменная sum , которая по умолчанию равна 0. В цикле определяем переменную-счетчик i и выполняем цикл, пока i не станет равна 6.
Обратите внимание на третью часть определения цикла - sum += i++ . Здесь мы прибавляем к переменной sum значение переменной i и потом увеличиваем значение i. Таким образом, мы нашли сумму чисел, но при этом обошлись без тела цикла.
Выражение инициализации может определять больше одной переменной. Например, определим две переменных и выведем на консоль их произведение:
#include int main() < int numbers[]; int sum <>; for (int i , j ; i < 6 && j < 10; i++, j++) < std::cout 1*5=5 2*6=12 3*7=21 4*8=32 5*9=45
Перебор значений в стиле for-each
Существует также особая форма цикла for , которая предназначена специально для работы с последовательностями значений. Эта форма имеет следующее формальное определение:
for(тип переменная : последовательность)
#include int main() < for (int n : ) < std::cout >
Здесь выражение как раз представляет последовательность значений - чисел int. Цикл перебирает всю эту последовательность и помещает каждое значение в переменную n , значение которой выводится на консоль.
Другой пример. Строка фактически представляет собой последовательность символов, которую также можно перебрать с помощью данной вида циклов:
#include int main() < for (char c : "Hello") < std::cout >
Здесь каждый символ строки помещается в переменную c, значение которой затем выводится на консоль.
В дальнейшем мы рассмотрим различные виды последовательности, которые можно перебирать с помощью данного вида циклов.
Цикл do
В цикле do сначала выполняется код цикла, а потом происходит проверка условия в инструкции while. И пока это условие истинно, то есть не равно 0, то цикл повторяется. Формальное определение цикла:
do < инструкции >while(условие);
#include int main() < int i ; do < std::cout while(i>0); >
Здесь код цикла сработает 6 раз, пока i не станет равным нулю.
Но важно отметить, что цикл do гарантирует хотя бы однократное выполнение действий, даже если условие в инструкции while не будет истинно. То есть мы можем написать:
int i ; do < std::cout while(i>0); >
Хотя у нас переменная i меньше 0, цикл все равно один раз выполнится.
Рассмотрим еще пример. В ряде консольных программ также реализован подобный цикл, который срабатывает, пока пользователь не введет какой-либо символ. Допустим, пользователь вводит числа, и программа должна вычислить среднее арифметическое чисел. И пусть пользователь может ввести неопределенное количество чисел, а если он захочет завершить ввод чисел, пусть введет символ "y" или "Y":
#include int main() < char reply <>; // ответ пользователя int count <>; // количество введенных чисел double number <>; // для ввода числа double total <>; // общая сумма чисел do < std::cout > number; // Вводим число total += number; // прибавляем к совокупному числу ++count; // увеличиваем количество введенных чисел на 1 std::cout > reply; // считываем ответ пользователя > while (reply != 'y' && reply != 'Y'); // пока пользователь не введет символ y и Y std::cout << "The average value is " << total/count
В данном случае считываем каждое число в переменную number, а затем прибавляем ее к переменной total, попутно увеличиваем счетчик чисел - count. После каждого ввода также ожидаем еще один ввод - если пользователь введет "y" или "Y", завершаем цикл и выводим среднее арифметическое чисел. Пример работы программы:
Enter a number: 6 Finish? (y/n): n Enter a number: 5 Finish? (y/n): y The average value is 5.5
Вложенные циклы for
Можно определять вложенные циклы. Например, выведем таблицу умножения с помощью вложенного цикла for :
#include int main() < for (int i ; i < 10; i++) < for(int j ; j < 10; j++) < std::cout std::cout >
1 2 3 4 5 6 7 8 9 2 4 6 8 10 12 14 16 18 3 6 9 12 15 18 21 24 27 4 8 12 16 20 24 28 32 36 5 10 15 20 25 30 35 40 45 6 12 18 24 30 36 42 48 54 7 14 21 28 35 42 49 56 63 8 16 24 32 40 48 56 64 72 9 18 27 36 45 54 63 72 81
Операторы continue и break
Иногда возникает необходимость выйти из цикла до его завершения. В этом случае можно воспользоваться оператором break . Например, нам надо подсчитать сумму чисел от 1 до 9, пока она не станет больше 20:
#include int main() < int result<>; for(int i; i < 10; i++) < result += i; std::cout 20) break; > >
Здесь когда значение переменной result станет больше 20 (то есть когда i будет равно 6), осуществляется выход из цикла с помощью оператора break :
1 3 6 10 15 21
В отличие от оператора break , оператор continue производит переход к следующей итерации. Например, нам надо посчитать сумму только нечетных чисел из некоторого диапазона:
#include int main() < int result <>; for (int i ; i std::cout // бесконечный цикл for - условие завершения отсутствует for (;;) < >// бесконечный цикл while - условие всегда равно true while (true) < >// бесконечный цикл do-while - условие всегда равно true do < >while (true);
Однако в этих случаях в зависимости от ситуации все равно может быть какое-то условие, при котором цикл может завершить работу. В этом случае для выхода из цикла может применяться оператор break . Например, пусть пользователь бесконечно может вводить числа, а программа выводит ему квадрат числа. Но если пользователь ввел 0, то выполним выход из цикла:
#include int main() < int n <>; // для ввода числа // бесконечный цикл while(true) < std::cout > n; // Вводим число // если пользователь ввел 0, то выходим из цикла if(n == 0) break; // иначе выводим квадрат числа std::cout >
While cin c как закончить ввод
JelalTkm → Нужна помощь
Imakf → Codeforces Round 906 Editorial
windva → Codeforces Round 899 (Div. 2) Editorial
islamicTerrorist69 → Facing problem in dynamic programming
_Firdavs_Aminov_ → Dark theme Codeforces
E869120 → To resubmit or Not to resubmit
k o_osaga → A Brief Inquiry into Online Connectivity
elshiko → Квалификационный раунд Yandex Cup 2023
Yandex → Yandex Cup 2023
-kirito- → TheForces Round #25 Editorial
Aphrim → 5 steps to reach expert
74TrAkToR → Codeforces Round #904 (Div. 2) Editorial
127.0.0.1 → Codeforces Round 907 (Div. 2)
SilverSurge → CSES Range Queries: Polynomial Queries
74TrAkToR → Codeforces Round #905 (Div. 1, Div. 2, Div. 3) Editorial
jli505 → IOI Gold Medalist Speaker Event
noomaK → IEEEXtreme 17.0 Problems Discussion
plourde27 → California Informatics Competition (CALICO) Fall '23
SkippedSolution → DP bitmask or DNC ?
Yhlas_Y → Favourite problem
_thor__ → Codeloop 2023: A Knockout Tournament Based Coding Contest
Yhlas_Y → IDE for cp
MikeMirzayanov → Please, read this
chenjb → Rescheduling of World Finals 22&23
anmolsainiii23 → Confused Regarding Cses 2nd DP Question
Блог пользователя trionprog
Ввод неизвестного количества данных C++
Автор trionprog, 11 лет назад ,
Пишу на С++. И тут появляется задание(тренировка СПБГУ#22 ) G,а в нём нужно вводить (я использую cin) неизвестное количество чисел,вот я и не знаю как отследить,что ввод был закончен.С файлом всё просто,а тут. Помогите
Комментарии (17)
Показать архивные | Написать комментарий?
11 лет назад , # |
← Rev. 4 → +19
int x; while (cin >> x) < // do smth >
UPD. Some info
11 лет назад , # ^ |
← Rev. 2 → -13
как проверить что ввод закончен?
11 лет назад , # ^ |
int x; while (cin >> x) < //do something >cout
11 лет назад , # |
С файлом всё просто,а тут.
Можешь это место по-подробнее объяснить?
11 лет назад , # ^ |
как я понял, топикстартеру с файлами проще потому что там EOF есть
11 лет назад , # ^ |
BackendDeveloper имеет в виду, что тут EOF есть в точно таком же виде, как и в файлах.
11 лет назад , # ^ |
← Rev. 5 → +4
В консоли это невозможно. UPD: слишком поздно написал UPD2: в консоли — имеется ввиду без файлов в codeblocks(или тому подобное) нажав на клавишу F9. UPD3: Извините за неправильный ответ. Раньше мне всегда твердили что это невозможно. Слова беру назад и большое спасибо Avitella и andreyv. Узнал что-то новое)
11 лет назад , # ^ |
В linux консоли есть комбинация клавиш CTRL + D. Так что все возможно 🙂
11 лет назад , # ^ |
← Rev. 2 → +9
- Ctrl+Z, Enter под Windows
- Ctrl+D под Linux
11 лет назад , # ^ |
спасибо, долго искал
11 лет назад , # |
← Rev. 2 → +8
Если нужен построчный ввод неизвестного количества данных поможет такое:
string s; while (getline(cin, s)) < //do domething >
11 лет назад , # ^ |
11 лет назад , # |
еще же scanf-ом можно
int x; while (scanf("%d", &x) == 1)< //do smth >
11 лет назад , # |
← Rev. 3 → +10
Можно использовать итераторы:
#include . std::istream_iterator it(cin); std::istream_iterator eos; // end-of-stream iterator int x; while (it != eos) < x = *it++; // >
11 лет назад , # ^ |
В олимпиадах я такого не видел)
11 лет назад , # ^ |
← Rev. 3 → +1
Моя не понимать. Вы тут объявили eos , но не инициализировали. Я правильно понимаю, что у него в стандартном конструкторе будет какая-то шняга, которая аналогична "бла-бла-бла" и позволяет понять, когда у нас конец ввода? Но тогда вопрос, в качестве так сказать инициализатора it мы передали cin , а почему без инициализатора будет то, что нам нужно? Объясните, пожалуйста, подробнее, а то лень копаться в референсах/исходниках и чекать у себя на компе, будет ли работать ваш пример. UPD. Скомипилилось и отработало. Объясните, почему.
11 лет назад , # ^ |
Вы понимаете правильно. Работает так потому что его так написали. Цитата отсюда A special value for this iterator exists: the end-of-stream; When an iterator is set to this value . has been constructed using its default constructor (without associating it with any basic_istream object).
Как правильно закончить вод чисел через цикл while(cin>>x)?
Собственно вопрос состоит в том чтобы правильно закончить цикл while. Мне нужно чтобы после ввода чисел(например 1 2 3 4 5) нажав на Enter ввод закончился.
Лучшие ответы ( 2 )
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
Ответы с готовыми решениями:
Как закончить цикл
пользователь вводит n значений через пробел и я не знаю сколько значений он введет например 1 23.
Как правильно отобразить данные через цикл
Я написал код, он читает количество совпадений в тексте string line =.
Как работает cin.peek, cin,get, cin.ignore, cin.clear?
Здравствуйте, товарищи и не товарищи!:) Я только начал изучать C++, а уже использую вещи, которые.
Как в цикле while закончить цикл
def loop(): print("Хотите ли вы посмотреть другие концовки?") time.sleep(2) mes =.
Форумчанин
8215 / 5045 / 1437
Регистрация: 29.11.2010
Сообщений: 13,453
Сообщение было отмечено no swear как решение
Решение
Сообщение от no swear
нажав на Enter
С таким условием не получится.
Можете завести число, обозначающее конец ввода последовательности, например 0. И условие изменить на
while(cin>>x && x)
Либо вводить спец. символ, обозначающий конец ввода. Для винды это Ctrl+ D
14 / 14 / 16
Регистрация: 26.01.2015
Сообщений: 213
Сообщение было отмечено no swear как решение
Решение
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
#include using namespace std; int main() { setlocale(LC_ALL,"RUS"); int x=0; int count=0; while(count5) { cin>>x; count++; } system("pause"); return 0; }
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
Помогаю со студенческими работами здесь
Как правильно создать массив через цикл for? Где ошибка?
Попалось на глаза следующее утверждение: Но по факту, массив просто заполняется рядом цифр.
Как правильно закончить поток?
Смотрите у меня будет класс в нем 2 действующих метода (ну и еще второстепенные), первый Exe этот.
Как правильно закончить программу?
Вот задание: Разработать программу, которая определяет три наибольших значения матрицы n×m и.
Как правильно закончить программу
Привет всем! Есть такой маленький вопрос, а есть ли большая(или маленькая) разница между вот.