C ++, поддержка мультиязычности / локализации - PullRequest
7 голосов
/ 25 марта 2011

Какой лучший способ добавить поддержку мультиязычности в программу на C ++?

Если возможно, язык следует читать из простого текстового файла, содержащего что-то вроде пар ключ-значение (§WelcomeMessage§ "Hello% s!").

Я думал о чем-то вроде добавления функции localizedString (key), которая возвращает строку загруженного языкового файла. Есть ли лучшие или более эффективные способы?

//half-pseudo code
//somewhere load the language key value pairs into langfile[]
string localizedString(key)
{
    //do something else here with the string like parsing placeholders
    return langfile[key];
}

cout << localizedString(§WelcomeMessage§);

Ответы [ 4 ]

10 голосов
/ 25 марта 2011

Самый простой способ без внешних библиотек:

// strings.h

enum
{
     LANG_EN_EN,
     LANG_EN_AU
};

enum
{
     STRING_HELLO,
     STRING_DO_SOMETHING,
     STRING_GOODBYE
};

// strings.c

char* en_gb[] = {"Well, Hello","Please do something","Goodbye"};
char* en_au[] = {"Morning, Cobber","do somin'","See Ya"};

char** languages[MAX_LANGUAGES] = {en_gb,en_au};

Это даст вам то, что вы хотите,Очевидно, вы можете прочитать строки из файла.Т.е.

// en_au.lang

STRING_HELLO,"Morning, CObber"
STRING_DO_SOMETHING,"do somin'"
STRING_GOODBYE,"See Ya"

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

// parse_strings.c

struct PARSE_STRINGS
{
    char* string_name;
    int   string_id;
}

PARSE_STRINGS[] = {{"STRING_HELLO",STRING_HELLO},
                   {"STRING_DO_SOMETHING",STRING_DO_SOMETHING},
                   {"STRING_GOODBYE",STRING_GOODBYE}};

Вышеприведенное должно быть немного проще в C ++, так как вы можете использовать метод перечисления классов toString () (или что бы то ни было - не можетенадо искать его).

Все, что вам нужно сделать, это проанализировать языковые файлы.

Надеюсь, это поможет.

PS: и получить доступ к строкам:

languages[current_language][STRING_HELLO]

PPS: извинения за половину c половина C ++ ответ.

6 голосов
/ 25 марта 2011

Библиотека ICU предназначена именно для этого.

5 голосов
/ 25 марта 2011

Предложение Space_C0wb0w является хорошим. В настоящее время мы успешно используем ICU для этого в наших продуктах.

Повторение вашего комментария к его ответу: Действительно, трудно сказать, что отделение интенсивной терапии "маленькое, чистое, несложное". В «ICU» возникает «случайная» сложность, возникающая из-за его интерфейса «Java-ish», но большая часть сложности и размера просто обусловлена ​​сложностью и размером проблемной области, к которой он обращается.

Если вам не нужна полная мощность ICU и вы заинтересованы только в «переводе сообщений», вы можете посмотреть GNU gettext , который, в зависимости от вашей платформы и требований лицензирования, может быть " меньшая, более чистая и менее сложная "альтернатива.

Проект Boost.Locale также является интересной альтернативой. Фактически, его функциональность « Messages Formatting » основана на модели gettext.

3 голосов
/ 25 марта 2011

Поскольку вы запрашиваете лучший способ (и не упомянул платформу), я бы порекомендовал GNU Gettext .

Возможно, это самая полная и зрелая библиотека интернационализации для программирования на C / C ++.

...