Дано предложение. Вывести буквы, которые содержатся в максимальном количестве слов
Нужно вывести буквы которые содержаться в максимальном количестве слов. Строки для меня тема новая поэтому не совсем понимаю как с ними работать попытался по советам сделать(создать массив для букв с нулевыми значениями и дальше проверять слова), но пишет что недопустимо для class, хотелось бы понять что это значит и как это исправить. Также я понимаю что с реализацией кода беда, но не понимаю как лучше сделать ее. Помогите пожалуйста. Заранее благодарю.
using namespace std;
int main() {
setlocale(LC_ALL, "RUS");
int max = INT_MIN;
string str;
string razdel = "!?,.:;- "; //Знаки пунктуации и пробел
cout << "Введите строку: ";
getline(cin, str); //Вводим строку
str += '.'; //Добавляем точку в конец строки
string alphabet = "abcdefghijklmnopqrstuvwxyzабвгдеёжзийклмнопрстуфхцчшщъыьэюя";
int** a = new int*[2];
for (int i = 0; i < 2; ++i) {
a[i] = new int[59];
}
for (int i = 0; i < 2; ++i) {
for (int j = 0; j < 59; ++j) {
a[1][j] = 0;
}
}
string::size_type pos = 0, k;
string::size_type max = 0;
k = str.find_first_of(razdel); //Ищем конец первого слова
while (k != string::npos) { //Пока находятся слова
string word = str.substr(pos, k - pos); //Копируем слово
for (int i = 0; i < word.length(); ++i) {
for (int j = 0; j < alphabet.length(); ++j) {
if(str[i] == alphabet[j]){
a[1][j]++;
}
}
}
k = str.find_first_of(razdel, pos); //Ищем конец следующего слова
}
for (int i = 0; i < 2; ++i) {
for (int j = 0; j < 59; ++j) {
if (a[1][j] > max) {
max = a[1][j];
}
}
}
cout << max; //Просто хотел проверить работает ли код и правильно ли выводит
system("pause");
return 0;
}
Ответы (1 шт):
Вот пример кода:
string str;
string razdel = "!?,.:;- "; //Знаки пунктуации и пробел
string alphabet = "abcdefghijklmnopqrstuvwxyzабвгдеёжзийклмнопрстуфхцчшщъыьэюя";
int size = alphabet.size();
int* a = new int[59]{ 0 };
cout << "Введите строку: ";
getline(cin, str); //Вводим строку
str += '.'; //Добавляем точку в конец строки
string::size_type pos = 0, k, t;
k = str.find_first_of(razdel); //Ищем конец первого слова
while (k != string::npos) { //Пока находятся слова
int j = 0;
//Задача заключается в том, чтобы найти букву, которая встречается в максимальном количестве слов
//Значит нужно искать букву в найденом слове, а если бы мы хотели подсчитать количество букв, то
//сначала проходили бы по слову, а потом уже по алфавиту.
do {
//Не нужно копировать подстроку в новую строчку.
//Можно просто пройтись по исходной строке от pos до k.
t = pos;
for (; t < k; ++t) {
if (str[t] == alphabet[j]) {
//a[j] - количество слов, в которых содержится буква под индексом j
a[j]++;
//т.к. букву на позиции pos мы рассмотрели, то чтобы её каждый раз не проверять мы подвинемся влево.
++pos;
//Т.к. все действия с буквой под индексом j мы произвели выше, то нет смысла проверять остальные буквы слова
break;
}
}
++j;
} while (j < size && t < pos); //если t == pos, то мы рассмотрели все слово
k = str.find_first_of(razdel, ++pos); //Ищем конец следующего слова
}
int max = INT_MIN;
int m_index = 0;
for (int j = 0; j < size; ++j) {
if (a[j] > max) {
max = a[j];
m_index = j;
}
}
cout << "Буква " << alphabet[m_index] << " найдена в " << max << " словах!" << endl;
Если вы не будете дополнять alphabet, то можно было избавится от цикла, который пробегает по алфавиту, а использовать коды букв по ASCII таблице, что гораздо быстрее было бы.
Так же лично я бы вместо find_first_of и строки под разделители написал бы функцию типа bool isRazdel(char symb) {...}, но это опять токи, если вы не собираетесь дополнять список разделителей.
Все идеи, которые я предложил хоть и ускоряют работу, но делают алгоритм менее гибким под изменения. (списка букв, разделителей)