- Как получить от пользователя строку с пробелами
- Строка с пробелами не читается
- Как ввести строку с пробелами через cin
- Ввод и вывод символьных строк в Си
- Создание и инициализация строки
- Как вывести строку
- Ввод строк
- Практика
- Как на C++ ввести с консоли строку с пробелами в тип string?
- Ввести и вывести строку с пробелами несколько раз
- 4 ответа 4
- Всё ещё ищете ответ? Посмотрите другие вопросы с метками c++ или задайте свой вопрос.
- Похожие
- Подписаться на ленту
Как получить от пользователя строку с пробелами
| Все способы изучить С++ |
Начинающие программисты даже не догадываются о том, какой огромный пласт в этой области скрыт от их глаз, и чего многие из новичков не увидят никогда, потому что это тёмная сторона программирования — чистый исходный код системного уровня… Подробнее.
Ввод строки в консольном приложении для пользователя не представляет особых сложностей — он просто печатает необходимое количество знаков и нажимает ENTER.
А вот для начинающего программиста на С++ всё может оказаться не так просто и привести к потере времени и сил на решение простой задачи. Зачем эта заморочка существует в С++, лично мне вообще непонятно. Но она существует. И заключается она в следующем.
Строка с пробелами не читается
Точнее, не читается она привычным для С++ способом. Например, если у вас есть переменная str , то вы можете попытаться прочитать в эту переменную строку, введённую пользователем:
И всё будет прекрасно работать, если пользователь введёт строку БЕЗ пробелов. Однако вас ждёт неприятность, если во вводимой строке будут пробелы. Например, если пользователь введёт:
то в переменной str после выполнения инструкции cin >> str; будет только 100 . То есть строка будет прочитана ТОЛЬКО до первого пробела.
ЛИРИЧЕСКОЕ ОТСТУПЛЕНИЕ
Вот за это я и не люблю С++. Ну зачем, спрашивается, так было делать?
Но отбросим лирику в сторону, и разберёмся, что же нам в этом случае делать?
А надо просто использовать другой способ. Например, такой:
В этом случае всё будет работать как надо:
Однако если вы думаете, что на этом ваши неприятности закончились, то зря. Это же С++. А не какой-нибудь Паскаль для лохов. У меня вообще иногда возникает подозрение, что создатель С++ преследовал цель не придумать мощный язык, а сделать так, чтобы программировать на нём могли только избранные. Иначе нафига в этом языке столько заморочек?
Итак, вот вам следующий нежданчик:
Здесь мы используем getline() , которая может читать целую строку (в том числе и с пробелами). Но, как вы думаете, сможем ли мы прочитать эту строку в этой программе?
Наверняка вы уже почувствовали подвох. И заключается он в том, что в этой программе вы не сможете прочитать строку str .
Но что же произойдёт? А то, что в переменную str запишется недочитанный буфер ввода, то есть строка » 200 300″ , и мы не сможем ввести новую строку.
Почему так? Потому что первый раз строка была прочитана не полностью, а только до первого пробела. Оставшиеся же символы остались в буфере, и новая строка не может быть введена, пока буфер полностью не прочитан.
Поэтому перед тем, как вводить новую строку, нам надо либо прочитать буфер до конца, либо очистить его.
Пробежаться до конца буфера можно, например, так:
Очистить буфер ввода cin можно, например, так:
то есть программа может быть примерно такой:
Ну что же, теперь, надеюсь, вы представляете, как пользователю ввести строку с пробелами в С++, и эта задачка не поставит вас в тупик.
Как ввести строку с пробелами через cin
Строку с пробелами можно ввести и привычным способом через cin , но для этого потребуется несколько переменных:
В этом случае вывод будет таким:
Как видите, так тоже можно. Правда пробелы при этом способе из введённой пользователем строки исключаются. Кроме того, не всегда удобно использовать несколько переменных для ввода. К тому же пользователю надо как-то знать, сколько пробелов допускается в строке. Ну или сильно усложнять код для обработки ввода.
На этом пока всё. Изучайте С++. Конечно, это далеко не самый простой язык. Но, с другой стороны, его изучение доставит вам много радости от неожиданных открытий, которых вы никогда не найдёте в более простых языках.
Так что я, например, использую Паскаль для работы (когда требуется сделать быстро и без лишних заморочек), а С++ для удовольствия, когда хочется немного помучиться, а результат и сроки не висят над тобой как Дамоклов меч…
Источник
Ввод и вывод символьных строк в Си
Пожалуйста, приостановите работу AdBlock на этом сайте.
Итак, строки в языке Си. Для них не предусмотрено отдельного типа данных, как это сделано во многих других языках программирования. В языке Си строка – это массив символов. Чтобы обозначить конец строки, используется символ ‘\0’ , о котором мы говорили в прошлой части этого урока. На экране он никак не отображается, поэтому посмотреть на него не получится.
Создание и инициализация строки
Так как строка – это массив символов, то объявление и инициализация строки аналогичны подобным операциям с одномерными массивами.
Следующий код иллюстрирует различные способы инициализации строк.
Рис.1 Объявление и инициализация строк
В первой строке мы просто объявляем массив из десяти символов. Это даже не совсем строка, т.к. в ней отсутствует нуль-символ \0 , пока это просто набор символов.
Вторая строка. Простейший способ инициализации в лоб. Объявляем каждый символ по отдельности. Тут главное не забыть добавить нуль-символ \0 .
Третья строка – аналог второй строки. Обратите внимание на картинку. Т.к. символов в строке справа меньше, чем элементов в массиве, остальные элементы заполнятся \0 .
Четвёртая строка. Как видите, тут не задан размер. Программа его вычислит автоматически и создаст массив символов нужный длины. При этом последним будет вставлен нуль-символ \0 .
Как вывести строку
Дополним код выше до полноценной программы, которая будет выводить созданные строки на экран.
Рис.2 Различные способы вывода строки на экран
Как видите, есть несколько основных способов вывести строку на экран.
- использовать функцию printf со спецификатором %s
- использовать функцию puts
- использовать функцию fputs , указав в качестве второго параметра стандартный поток для вывода stdout .
Единственный нюанс у функций puts и fputs . Обратите внимание, что функция puts переносит вывод на следующую строку, а функция fputs не переносит.
Как видите, с выводом всё достаточно просто.
Ввод строк
С вводом строк всё немного сложнее, чем с выводом. Простейшим способом будет являться следующее:
Функция gets приостанавливает работу программы, читает строку символов, введенных с клавиатуры, и помещает в символьный массив, имя которого передаётся функции в качестве параметра.
Завершением работы функции gets будет являться символ, соответствующий клавише ввод и записываемый в строку как нулевой символ.
Заметили опасность? Если нет, то о ней вас любезно предупредит компилятор. Дело в том, что функция gets завершает работу только тогда, когда пользователь нажимает клавишу ввод. Это чревато тем, что мы можем выйти за рамки массива, в нашем случае — если введено более 20 символов.
К слову, ранее ошибки переполнения буфера считались самым распространенным типом уязвимости. Они встречаются и сейчас, но использовать их для взлома программ стало гораздо сложнее.
Итак, что мы имеем. У нас есть задача: записать строку в массив ограниченного размера. То есть, мы должны как-то контролировать количество символов, вводимых пользователем. И тут нам на помощь приходит функция fgets :
Функция fgets принимает на вход три аргумента: переменную для записи строки, размер записываемой строки и имя потока, откуда взять данные для записи в строку, в данном случае — stdin . Как вы уже знаете из 3 урока, stdin – это стандартный поток ввода данных, обычно связанный с клавиатурой. Совсем необязательно данные должны поступать именно из потока stdin , в дальнейшем эту функцию мы также будем использовать для чтения данных из файлов.
Если в ходе выполнения этой программы мы введем строку длиннее, чем 10 символов, в массив все равно будут записаны только 9 символов с начала и символ переноса строки, fgets «обрежет» строку под необходимую длину.
Обратите внимание, функция fgets считывает не 10 символов, а 9 ! Как мы помним, в строках последний символ зарезервирован для нуль-символа.
Давайте это проверим. Запустим программу из последнего листинга. И введём строку 1234567890 . На экран выведется строка 123456789 .
Рис.3 Пример работы функции fgets
Возникает вопрос. А куда делся десятый символ? А я отвечу. Он никуда не делся, он остался в потоке ввода. Выполните следующую программу.
Вот результат её работы.
Рис.4 Непустой буфер stdin
Поясню произошедшее. Мы вызвали функцию fgets . Она открыла поток ввода и дождалась пока мы введём данные. Мы ввели с клавиатуры 1234567890\n ( \n я обозначаю нажатие клавиша Enter ). Это отправилось в поток ввода stdin . Функция fgets , как и полагается, взяла из потока ввода первые 9 символов 123456789 , добавила к ним нуль-символ \0 и записала это в строку str . В потоке ввода осталось ещё 0\n .
Далее мы объявляем переменную h . Выводим её значение на экран. После чего вызываем функцию scanf . Тут-то ожидается, что мы можем что-то ввести, но т.к. в потоке ввода висит 0\n , то функция scanf воспринимает это как наш ввод, и записывается 0 в переменную h . Далее мы выводим её на экран.
Это, конечно, не совсем такое поведение, которое мы ожидаем. Чтобы справиться с этой проблемой, необходимо очистить буфер ввода после того, как мы считали из него строку, введённую пользователем. Для этого используется специальная функция fflush . У неё всего один параметр – поток, который нужно очистить.
Исправим последний пример так, чтобы его работа была предсказуемой.
Теперь программа будет работать так, как надо.
Рис.4 Сброс буфера stdin функцией fflush
Подводя итог, можно отметить два факта. Первый. На данный момент использование функции gets является небезопасным, поэтому рекомендуется везде использовать функцию fgets .
Второй. Не забывайте очищать буфер ввода, если используете функцию fgets .
На этом разговор о вводе строк закончен. Идём дальше.
Практика
Решите предложенные задачи:
Для удобства работы сразу переходите в полноэкранный режим
Исследовательские задачи для хакеров
- Проверьте как ведет себя ваш компилятор в случае переполнения буфера.
Источник
Как на C++ ввести с консоли строку с пробелами в тип string?
Нужно создать программу определяющую является ли строка палиндромом(т.е. одинаково пишется как слева направо так и справа налево). Программа нормально работает, пока не встречается с пробелом. Я понял, что cin для стринговой строки вводит только до первого пробела. Может быть есть там какой нибудь эквивалет gets для string?
Помощь в написании контрольных, курсовых и дипломных работ здесь.
Как ввести строку с пробелами
char s1; char s2; int a; cin.getline(s1,50); cin>>a; .
Как ввести строку с пробелами?
Привет всем! Я пытался разными способами осуществить ввод строки с пробелами, но столкнулся с.
Как ввести из консоли строку известной длины?
Как ввести из консоли строку известной длины? Потоком.
Ввести строку с пробелами
Как ввести строук с пробелами? cin.getline работает через одно место. Если знаете, как с ним.
СПАСИБО. ПОМОГЛО. ПОЛУЧИЛОСЬ. ))
Добавлено через 3 минуты
вот здесь ты выкидываешь пробелы
а далее анализируешь строку не скорректировав размер строки
Тип string в консоли
Вот такие вопросы: 1. как правильно объявить string 2. записать в string слова и цифры с точками.
Записать строку с пробелами в string, с помощью потока.
Здравствуйте. Можно ли с помощью потока ввода записать строку с пробелами в тип string. Если да, то.
Строки (ввести строку разделенную пробелами, и в словах которые оканчиваются на АВС заменить СС)
ввести строку разделенную пробелами, и в словах которые оканчиваются на АВС заменить СС.
Ввести строку char с консоли
Добрый день! Помогите, пожалуйста. В моей программе используются переменные char* Я их.
Источник
Ввести и вывести строку с пробелами несколько раз
Нужно несколько раз ввести и вывести строку, которая содержит пробелы. Сколько раз ввести-вывести — это на усмотрение пользователя. Пытался так, но не работает.
Программа компилируется и цикл повторяется, но когда переменной i присваиваю значение 1 дальше строка не вводится. Выглядит это так:
И так пока я не выйду из цикла. Подскажите в чем ошибка и как исправить.
4 ответа 4
Дело в том, что все символы после числа и ‘\n’ вместе с ними после ввода 1 в
остаются во входном потоке.
Реально в Вашем случае там скорее всего будут символы \r\n.
непосредственно перед while(i==1); и все заработает.
Вообще не рекомендуется использовать std::getline и >> оператор.
Вот здесь есть ответ на Ваш вопрос.
Считывание с клавиатуры строк, состоящих из слов, разделенных пробелами можно выполнить с помощью приведенного ниже фрагмента программы.
Всё ещё ищете ответ? Посмотрите другие вопросы с метками c++ или задайте свой вопрос.
Похожие
Подписаться на ленту
Для подписки на ленту скопируйте и вставьте эту ссылку в вашу программу для чтения RSS.
дизайн сайта / логотип © 2021 Stack Exchange Inc; материалы пользователей предоставляются на условиях лицензии cc by-sa. rev 2021.11.3.40639
Нажимая «Принять все файлы cookie» вы соглашаетесь, что Stack Exchange может хранить файлы cookie на вашем устройстве и раскрывать информацию в соответствии с нашей Политикой в отношении файлов cookie.
Источник