возникла проблема с созданием программы-палиндрома на c ++

Привет, это мой код для программы палиндрома:

void palindrome()
{
    string input;
    bool checkInput, palindrome;
    palindrome = true;
    do
    {
        checkInput = false;
        cout << "Enter a word, phrase or sentence :\n";
        getline(cin, input);

        for (unsigned int i = 0; i < input.size(); i++)
        {
            if (input[i] < 65 || input[i] > 90 && input[i] < 97 || input[i] > 122)
            {
                checkInput = true;
            }
        }



    } while (checkInput);

    for (unsigned int i = 0, j = input.size() - 1; i < input.size(); i++, j--)
    {
        if (input[i] != input[j] && input[i] + 32 != input[j] && input[i] - 32 != input[j])
        {
            palindrome = false;
            break;
        }
    }

    if (palindrome)
    {
        cout << "\n\nTo consider only letters and digits:\n";
        cout << input << "\nYes, it is palindrome!\n";
        cout << "\t\t Press <Enter> key back to menu";
        fflush(stdin);
        cin.get();
    }
    else
    {
        cout << "\n\nTo consider only letters and digits:\n";
        cout << input << "\nNOPE, it's not palindrome\n";
        cout << "\t\t Press <Enter> key back to menu";
        fflush(stdin);
        cin.get();
    }
}

и когда мой ввод - гоночная машина, он читает и говорит, что это палиндром, но когда мой ввод - гоночная машина (с пробелом), он не читает и говорит, что это не палиндром. Я намерен игнорировать все пробелы. Любая помощь будет высоко ценится! Заранее спасибо!

** отредактировано, поэтому я переключил свой ввод cin >> на getline (cin, input), и он не позволяет мне вводить мои слова или фразы


person corkiiunranked    schedule 17.03.2015    source источник
comment
Один совет, чтобы сделать ваш код более читаемым, - использовать символьные литералы вместо чисел, например. input[i] < 'A' вместо input[i] < 65.   -  person Simon    schedule 17.03.2015
comment
@corkiiunranked, Есть 2 ответа, которые решают вашу проблему и следуют совету Саймона.   -  person Jagannath    schedule 17.03.2015
comment
Я бы предпочел использовать isalnum из <cctype> вместо ручной проверки.   -  person martin    schedule 17.03.2015


Ответы (3)


Эта проблема

Палиндром - это слово, которое пишется вперед и назад одинаково. Следовательно, вы можете быть уверены, что, идя извне внутрь, буквы должны быть одинаковыми, пока вы не исследуете ту же букву (общее количество букв нечетное) или предметы / экзаменаторы / маркеры для поиска букв (давайте назовем их итераторами) крест-накрест.

Как вы исследуете пару букв снаружи внутрь? Используя цикл индексации от первой до последней позиции в тандеме с циклом индексации последний-первый.

Как вы это делаете (реализация)

Предположим, у нас есть две переменные, которые действуют как итераторы, i и j. я буду двигаться вперед, а j - назад. Они начнутся с противоположных концов:

#include <iostream>
#include <string>
#include <algorithm>

int main()
{
    //This is where our word will be.
    std::string str;
    
    //Get input
    std::cout << "Input your word, please!" << std::endl;
    std::getline(std::cin, str);
    
    //Let's use std::erase to take away our whitespaces from the
    //C++11 library <algorithm>
    str.erase(remove_if(str.begin(), str.end(), isspace), str.end());
    
    //Initialize i and j, our iterators
    //I use auto because the iterator type is long. It's a reason why auto was invented.
    auto i = str.begin();
    auto j = str.end() - 1;
    //You see, str.end() is actually the END, and not the last letter.
    //That's why it has a -1.
    
    bool is_palindrome = true;
    
    while (i < j) //While the two haven't crossed yet
    {
        //This std::cout shows you what i and j are at each repeat
        std::cout << "i = " << *i << " ||| j = " << *j << std::endl;
        
        //If the two characters marked by the two iterators are not equal
        if (*i != *j)
        {
            is_palindrome = false;
            break;
        }
        else
        {
            //Let's continue.
            ++i;
            --j;
        }
    }
    
    //If the loop gets to this point successfully, it's a palindrome.
    if (is_palindrome)
        std::cout << str << " is a palindrome!" << std::endl;
    else
        std::cout << str << " is not a palindrome." << std::endl;
        
    return 0;
}

Надеюсь, это вам поможет. Не забудьте компилировать с -std = c ++ 11 для функций C ++ 11!

person Cinch    schedule 17.03.2015

Может быть, это сработает, если вы сначала удалите все пробелы после прочтения ввода?

#include <algorithm>

str.erase(remove_if(str.begin(), str.end(), isspace), str.end());

Пробелов нет в проверяемых значениях ASCII, поэтому цикл while заканчивается на первом пробеле.

person J-Eibe    schedule 17.03.2015
comment
хорошо, допустим, у меня есть строковый ввод, так что это код: input.erase (remove_if (input.begin (), input.end (), isspace), input.end ()); почему говорится, что remove_if не определен? - person corkiiunranked; 17.03.2015
comment
вы должны включить ‹algorithm› - person J-Eibe; 17.03.2015

Посмотрите, работает ли это.

    for (unsigned int i = 0, j == input.size() - 1; i < input.size();)
    {
        //Ignore spaces
        if (input[i] == ' ')
        {
           ++i; continue;
        }
        if (input[j] == ' ')
        {
           --j;continue;
        }

        //Automatic palindrome analysis 
        if (input[i] != input[j])
        {
            palindrome = false;
            break;
        }
        ++i;--j;
    }
person Jagannath    schedule 17.03.2015