В качестве практики работы со строками напишем небольшую программу для подсчета слов.
#include #include #include int main() < std::string text; // Исходный текст std::cout ; // разделители слов std::vector words; // вектор для хранения слов size_t start < text.find_first_not_of(separators) >; // начальный индекс первого слова while (start != std::string::npos) // проходим, пока в строке не окажется других символов, кроме separators < size_t end = text.find_first_of(separators, start + 1); // находим, где кончается слово if (end == std::string::npos) // если НЕ найден ни один из символов-разделителей end = text.length(); // устанавливаем переменную end на конец текста words.push_back(text.substr(start, end — start)); // добавляем в вектор слово start = text.find_first_not_of(separators, end + 1); // находим начальный индекс следующего слова и переустанавливаем start >// выводим количество слов std::cout >
Вначале определяется переменная text, которая будет содержать введенную с консоли строку:
9.4 Количество слов. «Поколение Python»: курс для начинающих. Курс Stepik
std::string text; // Исходный текст std::cout >> «Enter some text: «; std::getline(std::cin, text);
Определяем строку разделителей, такие как знаки пунктуации, пробелы, символ перевода строки, которые не являются словами:
const std::string separators< » ,;:.»!?’*n» >; // разделители слов
Стоит отметить, что символ перевода строки здесь определен больше для демонстрации, поскольку при вводе выше через std::getline ввода строки будет завершен, когда мы нажмем на Enter. Соответственно введенная строка никогда не будет содержать символ n. Однако если мы изменим символ, до которого идет ввод строки через std::getline , или в качестве источника ввода будет использовать, например, текст из файла, тогда символ перевода строки тоже будет играть определенную роль.
Поскольку количество слов может быть неопределенным, то для хранения слов определяем вектор:
std::vector words; // вектор для хранения слов
Перед обработкой введенного текста фиксируем индекс первого символа первого слова в тексте. Для этого применяется функция find_first_not_of() , которая возвращает первый индекс любого символа, который не входит в строку separators:
size_t start < text.find_first_not_of(separators) >; // начальный индекс первого слова
Далее в цикле while смотрим, является ли полученный индекс действительным индексом:
while (start != std::string::npos)
Например, если в строке одни только символы из набора separators, тогда функция find_first_not_of() возвратит значение std::string::npos , что будет означать, что в тексте больше нет непунктационных знаков.
И если start указывает на действительный индекс начала слова, то находим индекс после последнего символа слова, который помещаем в переменную end:
size_t end = text.find_first_of(separators, start + 1); // находим, где закончилось слово
Для нахождения позиции окончания слова используем функцию find_first_of() , которая возвращает первую позицию любого символа из separators, начиная с индекса start+1
Уроки C++ / #10 урок — Строки и символы
Причем может быть, что функция find_first_of() не найдет ни одного символа из separators (например, слово является поседним в тексте, и после него нет никаких знаков пунктуации или пробелов), в этом случае конечный индекс равен длине текста.
if (end == std::string::npos) // если НЕ найден ни один из символов-разделителей end = text.length(); // устанавливаем переменную end на конец текста
После того, как мы нашли начальный индексы слова и его конец, то с помощью функци substr() получаем подстроку между этими индексами, добавляем слово в вектор, переустанавливаем start на начальный индекс следующего слова и повторяем действия цикла:
words.push_back(text.substr(start, end — start)); // добавляем в вектор слово start = text.find_first_not_of(separators, end + 1); // находим начальный индекс следующего слова и переустанавливаем start
В конце выводим количество найденных слов и сами слова.
Пример работы программы:
Enter some text: When in Rome, do as the Romans do. Text contains 8 words: When in Rome do as the Romans do
Источник: metanit.com
Подсчитать количество слов в строке (Си)
Слово — последовательность символов, разделенных пробелами. Под пробелами тут будем понимать символ пробела (не табуляции или чего-то еще). Посчитать число пробелов (и групп пробелов) — неправильно. Ведь строка без пробелов может быть пустой, а может содержать одно слово. Строка с одним словом может содержать ноль пробелов, а также 1 или 2 группы пробелов (перед и после слова).
Правильно — считать пары <группу пробелов> Решение будет таким: 1. Считаем с текущей (изначально нулевой) позиции в строке длину группы пробелов, прибавляем ее к текущей позиции. За счет этого группа «пропущена».
2. Считаем с текущей позиции длину группы непробельных символов ( word_length ).
3. Если word_length болшье нуля — увеличиваем счетчик слов. Прибавляем длину слова к текущей позиции — за счет этого слово «пропущено».
4. Процесс повторяется пока счетчик не станет больше длины строки. Ясно что подсчет пробелов и непробелов — это две разные функции, которые отличаются лишь оператором сравнения текущего символа. Красивое решение заключается в передаче этой функции в качестве параметра указателя на функцию сравнения. Функции сравнения при этом можно описать так:
int is_space(char c) < return c == ‘ ‘; >int is_not_space(char c)
Имея их совсем несложно добавить к пробельным символам что-то еще — табуляции, короткие пробелы, переводы строки т.п. Функция подсчета тогда может быть описана так:
int count_start_if(char* str, int (*pred)(char)) < int count = 0; while (*str != 0) < if (pred(*str)) < count++; str++; >else break; > return count; >
Первым аргументом она принимает указатель, однако в качестве него может быть передана подстрока так: return c == ‘ ‘; >int is_not_space(char c) < return 0 == is_space(c); >int count_start_if(char* str, int (*pred)(char)) < int count = 0; while (*str != 0) < if (pred(*str)) < count++; str++; >else break; > return count; > int count_words(char* str) < int length = strlen(str); int count = 0; int i = 0; while (1) < int spaces_count = count_start_if( i += spaces_count; if (i >= length) < break; >int word_length = count_start_if( if (word_length > 0) < count++; >i += word_length; if (i >= length) < break; >> return count; > int main()
Пример выполнения программы:
Источник: pro-prof.com
Посчитать количество слов в строке
Даже если заменить ввод данных на правильный (getline), то эта программа считает число пробелов в строке, а не слов. Очевидно, что с другим символом-разделителем дело обстоит так же, т.е. вы тестируете на упрощенных наборах данных
25 ноя 2018 в 13:44
3 ответа 3
Сортировка: Сброс на вариант по умолчанию
cin >> name;
считывает только одно слово, до пробела.
Воспользуйтесь для чтения строки getline .
Отслеживать
ответ дан 25 ноя 2018 в 13:15
215k 15 15 золотых знаков 117 117 серебряных знаков 228 228 бронзовых знаков
Теперь данный код считает количество символов
25 ноя 2018 в 13:23
Какая-то ерунда. Покажите код и вводимые данные.
25 ноя 2018 в 13:26
Код выше приложен. Вводимые данные случайные
25 ноя 2018 в 13:28
Код выше использует >> . Как вы используете getline ?
25 ноя 2018 в 13:33
Смотрите сами: ideone.com/km1HnK Все, как заказано — сколько пробелов введено, столько и выводит.
25 ноя 2018 в 13:43
Подсчет слов это классика жанра (один из примеров в K int in_word = 0, c; size_t cnt = 0; while (c = *str++) < if (strchr(delim, c)) < if (in_word) in_word = 0; >else < if (!in_word) < in_word = 1; cnt++; >> > return cnt; >
Отслеживать
ответ дан 25 ноя 2018 в 16:05
45.6k 6 6 золотых знаков 45 45 серебряных знаков 115 115 бронзовых знаков
std::cin >> name;
То у тебя будет только строка до ближайшего пробела, а если тебе нужен текст до ввода ‘Enter’:
std::string name; std::getline(std::cin, name);
#include #include int main()
Отслеживать
ответ дан 16 мар в 8:06
polySladkiy polySladkiy
51 5 5 бронзовых знаков
- c++
- строки
-
Важное на Мете
Похожие
Подписаться на ленту
Лента вопроса
Для подписки на ленту скопируйте и вставьте эту ссылку в вашу программу для чтения RSS.
Нажимая «Принять все файлы cookie» вы соглашаетесь, что Stack Exchange может хранить файлы cookie на вашем устройстве и раскрывать информацию в соответствии с нашей Политикой в отношении файлов cookie.
Источник: ru.stackoverflow.com