Урок 57. Введение в std::string

   ⁄ 

 Обновлено 29 Апр 2017  ⁄ 

 ⁄   17 

⁄   4276

Ваша первая программа на языке C++, вероятно, была:

Не так ли? Но что такое «Hello, world!»? «Hello, world!» — это последовательность символов, называемых строкой или string. В C++ мы используем строки для представления текста (имен, адресов, слов и предложений). Строковые литералы (такие как «Hello, world!») помещаются между двойными кавычками.

Поскольку их часто используют в программах, большинство современных языков программирования имеют встроенный тип данных string. В C++ есть свой, но не как часть основного языка, а как часть стандартной библиотеки.

std::string

Чтобы иметь возможность использовать строки в C++, сначала нужно подключить заголовочный файл <string>. Как только это будет сделано, мы сможем определять переменные типа std::string.

Как и с обычными переменными, вы можете инициализировать или присваивать им значения:

Строки также могут содержать числа:

Стоит отметить, что числа string обрабатываются как текст, а не как числа, и, следовательно, ими нельзя манипулировать как с обычными числами (например, вы не сможете их умножать). C++ автоматически не преобразовывает их в значения типов int или float.

Ввод/вывод строк

Строки выводить можно с помощью std::cout:

Результат:

My name is: Sasha

А вот с std::cin уже немного по-другому. Рассмотрим следующий пример:

Результаты пробного запуска этой программы:



Enter your full name: Sasha Mak
Enter your age: Your name is Sasha and your age is Mak

Хм, это неправильно! Что же случилось? Оказывается, оператор >> извлечения строки из cin возвращает символы только до первого пробела. Любые другие символы остаются внутри cin, ожидая следующего извлечения.

Поэтому, когда мы использовали оператор >> для извлечения строки в переменную myName, только «Sasha» был извлечен, «Mak» осталось внутри std::cin, ожидая следующего извлечения. Когда мы использовали оператор >> снова, чтобы извлечь строку в переменную myAge, мы получили «Mak» вместо «25». Если бы мы сделали третье извлечение, мы бы получили «25».

Использование std::getline() для ввода текста

Чтобы извлечь полную строку ввода — лучше использовать функцию std::getline(). Она принимает два параметра: первый – std::cin, второй — переменная string.

Вот та же программа, что выше, но уже с использованием std::getline():

Теперь программа работает как надо:

Enter your full name: Sasha Mak
Enter your age: 25
Your name is Sasha Mak and your age is 25

Использование std::cin и std::getline()

Чтение вводов как с std::cin, так и с std::getline иногда может создавать неожиданные результаты. Рассмотрим следующее:

Возможно, вы удивитесь, но когда запустите эту программу и она попросит вас ввести ваше имя, она не будет ожидать вашего ввода, а сразу выведет результат (просто пробел вместо вашего имени)! Пробный запуск:

Pick 1 or 2: 2
Now enter your name: Hello, , you picked 2

Почему так? Оказывается, когда вы вводите числовое значение с помощью cin, cin не только захватывает числовое значение, но и символ новой строки. Так что, когда мы ввели 2, cin фактически получил «2\n». Затем он извлек значение 2 в переменную, оставляя \n (символ новой строки) во входном потоке. Затем, когда std::getline будет считывать данные для myName, он увидит в потоке «\n», и подумает, что мы, должно быть, ввели просто пустую строку! А это определенно не то, что должно быть на самом деле.

Хорошее эмпирическое правило состоит в том, что после считывания числового значения с std::cin удалите символ новой строки из потока. Это можно осуществить так:

Если мы вставим эту строку непосредственно после считывания переменной, символ новой строки будет удален из потока, и программа будет работать как надо!

Правило: Если вы вводите числовые значения, используя std::cin, не забывайте удалять символ новой строки с помощью std::cin.ignore().

Добавление строк

Вы можете использовать оператор +, чтобы объединить две строки, или оператор +=, чтобы добавить одну строку к другой.

Вот пример того и другого, также показано, что произойдет, если вы попытаетесь использовать оператор +, чтобы добавить две числовые строки:

Результат:

4412
44 cats



Обратите внимание, оператор + соединил строки «44» и «12» в «4412». Он не добавлял их как числа.

Длина строк

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

Результат:

Sasha has 5 characters

Обратите внимание, вместо запроса длины строки как length(myName), мы пишем myName.length().

Функция запроса длины строки не является обычной функцией, как те, которые мы использовали до этого момента — это особый тип функции std::string, который называется функцией-членом. Мы рассмотрим этот тип функций и то, как создавать собственные функции-члены, более подробно в следующих уроках.

Тест

Напишите программу, которая спрашивает у пользователя его имя-фамилию и возраст. В результате также укажите пользователю, сколько лет он прожил с каждой буквы своего имя-фамилии (чтобы было проще, пробелы тоже считаются буквами).

Например:

Enter your full name: John Doe
Enter your age: 46
You've lived 5.75 years for each letter in your name.

Уточнение: То есть, если возраст 46, а имя «John Doe» (8 букв вместе с пробелом), то 46 делим на 8. Получаем 5.75.

Ответ

Оценить статью:

Звёзд: 1Звёзд: 2Звёзд: 3Звёзд: 4Звёзд: 5 (28 оценок, среднее: 5,00 из 5)
Загрузка...
Подписаться на обновления:

Комментариев: 17

  1. Sergey Groysman:

    Юрий, доброго дня. Подскажите, в чём разница в данных записях, если работают обе, переводя число в double и мы получаем на выходе число с плавающей точкой.

    вместо

    можно ли обходиться в принципе без static_cast?
    Спасибо.

    1. Юрий:

      Привет. Ответ на ваш вопрос находится в уроке 56.

  2. Серж:

    Перечитал урок 7.
    Проблема 1
    Как использовать русский язык в консоли C++?
    Слово в слово повторено как в программе выше и где сказано что всё работает.
    У меня в CodeBlocks не работает. Возможно в студии будет работать , не проверял.
    Остается в уроке 7 прочитать совет в самом низу: Во-первых, спросите Google…

    1. Li4ik:

      Верно, если Google не поможет, спросите на StackOverflow. Код рабочий, если у вас не работает, значит у вас уже специфическая проблема: возможно кодировка в Code:Blocks у вас не та, что нужно. Возможно, у вас что-то подключено (плагин, расширение или что-либо другое), что блокирует корректное выполнение setlocale.

      1. Серж:

        Ясно, спасибо. Подключена русификация интерфейса и все. Пока не искал решения проблемы, т.к. это не сильно влияет на изучение.
        Огромное спасибо за такой нужный труд по переводу и поддержанию сайта с этим учебным курсом. Из всего что я находил ,это самое лучшее. Спасибо!!!

        1. Li4ik:

          Пожалуйста 🙂

          Попробуйте отключить русификацию интерфейса и посмотрите какая у вас кодировка стоит — сбросьте всё до значений по умолчанию. И если уже никак, то вы знаете, где искать.

  3. Максим:

  4. Ka4:

    Скажите, пожалуйста, что я не так сделал!

    1. Li4ik:

      Ваш код рабочий. Результаты совпадают.

      Что не так:

      1. У вас функция im9_famili9 выполняет сразу два задания: получает строку и высчитывает её длину. (Функция должна выполнять одно задание)

      2. Функции result нужно было присвоить тип void и ничего не возвращать, а сразу выводить результат в консоль. А то у вас result выводит результат и возвращает его еще в main() — зачем и почему? В main вы с переменной z ничего не делаете, её объявление вообще не нужно.

      Всё остальное гуд.

      1. Ka4:

        Точно..
        Спасибо больше!)
        Отличные уроки!!!
        Догоняю программу в ВУЗе с помощью этого сайта!

        1. Li4ik:

          Если честно, то я тоже свою программу из универа догнал и перегнал именно по этим урокам 🙂

  5. Герман:

    Спасибо!!!

    1. Li4ik:

      Пожалуйста 🙂

  6. Герман:

    Уважаемый автор, почему при выводе в консоль значение переменной myName, не поддерживается кириллица!

    1. Li4ik:

      Нужно подключить Windows.h (заголовочный файл) и прописать строчки:

      Вот всё работает:

      1. Серж:

        Почему-то в CodeBlocks 17.12 выводит этим способом кракозябры как на ввод ,так и на вывод. Если использовать setlocale(LC_ALL, "rus"); или setlocale(LC_ALL, ""); вывод идет на русском , а на ввод кракозябры ,если использовать
        SetConsoleCP(1251);
        SetConsoleOutputCP(1251);
        то даже при подключенном setlocale(LC_ALL, "rus"); все равно кракозябры.

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

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

ПОДПИСЫВАЙТЕСЬ

НА КАНАЛ RAVESLI В TELEGRAM

@ravesli

ПОДПИСАТЬСЯ БЕСПЛАТНО