Манипулирование строками с гласными, не работающими должным образом - PullRequest
0 голосов
/ 13 июня 2019

Приведенная ниже программа предназначена для того, чтобы сделать все символы строчными буквами, удалить все гласные, а затем распечатать точку перед каждой буквой.Например, ввод «зонтика» станет «.mbrll».Но когда я ввожу "tour", 'u' не удаляется.

char ChangeToLow(char letter) {
  if(letter <= 'Z' && letter >= 'A')
    return letter - ('A' - 'a');
  return letter;
}
int main()
{
    string name;
    cin>>name;
    for (int i = 0 ; i < name.length() ; i++)
    {
        name[i] = ChangeToLow(name[i]);
        if (name[i] == 'y' || name[i] == 'a'|| name[i] == 'u'|| name[i] == 'i'|| name[i] == 'e'|| name[i] == 'o')
        {
            name.erase(i,1);
        }
    }
    for (int i = 0 ; i < name.length() ; i++)
        {
          cout<<'.'<<name[i];
        }
}

Я ожидаю вывод ".tr", но вместо этого он печатает ".tur".Заранее спасибо.

Ответы [ 2 ]

4 голосов
/ 13 июня 2019

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

tour indexes

Ваш счетчик циклов, i, был увеличен до 2 после того, как вы удалили 'o' из тура, и name[i] теперь равно 'r'. Один из способов избежать такого поведения - уменьшить i при удалении гласной.

0 голосов
/ 13 июня 2019

У меня есть предложение для вас. Во-первых, вы не должны вставлять using namespace std; в ваш код. Это только добавляет путаницы и считается плохой практикой. Я думаю, что было бы неплохо, если бы вы решили изучить STL, если ваша цель - углубленное изучение C ++. Что касается ошибки, я думаю, что уже опубликованный ответ показывает ваши неправильные предположения.

#include <iostream>
#include <cstdlib>
#include <locale>
#include <set>
#include <algorithm>

int main()
{
        std::string name;
        std::cin>>name;

        std::set<char> vowels={'a','u','i','e','o'};
        std::transform(name.begin(), name.end(), name.begin(), [](auto v){ return std::tolower(v, std::locale());});

        auto iter=std::remove_if(name.begin(), name.end(), [&vowels](auto v){ return vowels.find(v)!=vowels.end();});
        name.erase(iter,name.end());

        for (int i = 0 ; i < name.length() ; i++)
        {
                std::cout<<'.'<<name[i];
        }
        return EXIT_SUCCESS;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...