С++ конвертирует ASCII в азбуку Морзе

Я делаю программу, которая преобразует буквы, цифры и знаки препинания в азбуку Морзе.

С буквами и цифрами все работает так, как я хочу.

Но со знаками препинания я не могу заставить его работать должным образом. Я надеялся, что кто-то может взглянуть на мой код и помочь мне.

#include <iostream>
#include <cstring>
#include <sstream>
using namespace std;



    char ch;
    string morseWord = "";

    for(unsigned int i=0; i < word.length(); i++)
    {
        if(isalpha(word[i]))
        {
            ch ;
        }
    }
    return morseWord;
}


    char ch;
    string morseWord = "";

    for(unsigned int i=0; i < word.length(); i++)
    {
        if(isdigit(word[i]))
        {
            ch = word[i];
            ch = toupper(ch);
            morseWord += morseCode[ch - '0'];
            morseWord += " ";

    string morseWord = "";

    for(unsigned int i=0; i < word.length(); i++)
    {
        if(ispunct(word[i]))
        {
            ch = word[i];
            ch = toupper(ch);
            morseWord += morseCode[ch - '.'];
            morseWord += " ";
        }
    }
    return morseWord;
}



int main()
{   
    stringstream ss;
    string sentence;
    string word = "";

    code: " << endl;

    while(ss >> ToMorse(word) << endl;
        cout << PunctuationToMorse(word) << endl;
}

person Lasse Hedegaard    schedule 11.02.2017    source источник
comment
Добро пожаловать в Stack Overflow. Пожалуйста, найдите время, чтобы прочитать Тур и обратиться к материалам из Справочный центр что и как здесь можно спросить.   -  person πάντα ῥεῖ    schedule 11.02.2017
comment
Но со знаками препинания я не могу заставить его работать должным образом. В чем ваша настоящая проблема? Каковы входные данные, ожидаемый результат и фактический результат?   -  person πάντα ῥεῖ    schedule 11.02.2017
comment
На данный момент я хочу иметь возможность вводить: точку, вопросительный знак и восклицательный знак. Когда я ввожу точку, она отлично ее преобразует. Но когда я ввожу два других, это дает мне: ?U???.   -  person Lasse Hedegaard    schedule 11.02.2017
comment
Вместо сопоставления через прямые индексы массива вы должны предоставить std::map<char,std::string> для сопоставления строк кода Морзе с определенными символами ASCII. Тогда эту карту можно было бы использовать с одной функцией.   -  person πάντα ῥεῖ    schedule 11.02.2017


Ответы (1)


Ваша основная проблема заключается в том, что вы пропустили фигурные скобки для цикла while() в своей функции main():

while(ss >> word) { // <<<< Put an opening brace here
    cout << EnglishToMorse(word) << endl;
    cout << NumbersToMorse(word) << endl;
    cout << PunctuationToMorse(word) << endl;
} // <<<<< ... and a closing brace here

Как правило, лучшим подходом будет:

Сопоставьте все известные символы, которые можно преобразовать в азбуку Морзе с помощью std::map<char,std::string>, и используйте одну функцию для их обработки:

string CharToMorse(char c) {
    static const std::map<char,std::string> morseCode = {
        { 'A', ".-" } ,
        { 'B' , "-..." } , 
        { 'C', "-.-." } ,
        // ...
        { 'Z', "--.." },
        { '0', ".----" } , 
        { '1', "..---" } , 
        { '2', "...--" } ,
        // ...
        { '9', "-----" } ,
        { ' ', "......." } // Consider to support spaces between words
        { '.', ".-.-.-" } ,
        { '!' , "..--.." } , 
        { '?' , "-.-.--"}
    };

    auto morseString = morseCode.find(toUpper(c));
    if(morseString != morseCode.end()) {
        return morseString->second;
    }
    return "";
}

и используйте его как:

int main() {   
    stringstream ss;
    string sentence;

    cout << "Enter a English word, number or punctuation: ";
    getline(cin, sentence);
    ss << sentence;
    cout << "Morse code: " << endl;
    char c;
    while(ss >> c) {
        cout << CharToMorse(c);
    }
    cout << endl;
}

Проблема с вашим фактическим кодом заключается в том, что он делает предположения, полагаясь на сопоставления таблиц кодов символов ASCII, и что 'Z' - 'A' == 25.
Это не гарантируется стандартом C++ и делает ваш код непереносимым (см. здесь также).

person πάντα ῥεῖ    schedule 11.02.2017
comment
Следующим шагом эволюции будет отделение базовых данных Морзе от их представления. Вместо std::string сопоставленным типом std::map может быть класс, подобный MorseCode, который внутренне хранит последовательность точек и дефисов, например. элемент данных private типа std::bitset. А затем предоставьте функцию, например std::string ToString(MorseCode const& morse_code). - person Christian Hackl; 11.02.2017
comment
@Кристиан Конечно. Давайте сделаем это простым для новичков. Вы настоящий энтузиаст ;-). Не забывайте, что с таким классом std::set<MorseCode> должно быть достаточно. - person πάντα ῥεῖ; 11.02.2017
comment
@LasseHedegard Прекратите редактировать мой ответ, пожалуйста. Вместо этого улучшите свой вопрос. - person πάντα ῥεῖ; 13.02.2017