Как прочитать строку utf-8 из xml с помощью rapidxml?

Мой вопрос такой же, как этот вопрос без ответа?

Как читать XML-значения Unicode с помощью rapidxml

Но содержимое моего XML закодировано в UTF-8. Я новичок в MS Visual Studio, C++.

Мой вопрос: как мы читаем строку UTF-8 в строку типа wchar_t?

Скажем, я определяю такую ​​структуру,

typedef struct{
    vector<int> stroke_labels;
    int stroke_count;
    wchar_t* uni_val;
}WORD_DETAIL;

и когда я читаю значение из xml, я использую..

WORD_DETAIL this_detail;
this_detail.uni_val=curr_word->first_node("labelDesc")->first_node("annotationDetails")->first_node("codeSequence")->value();

Но сохраняемые строки utf-8 не такие, как ожидалось. Это испорченные персонажи.

Мои вопросы:

  1. Как я могу использовать rapidxml для чтения значений Unicode/Utf-8?
  2. Существуют ли более простые парсеры xml, которые делают то же самое?
  3. Любой пример кода будет глубоко оценен.

В разделе 2.1 здесь упоминается

«Обратите внимание, что RapidXml не выполняет декодирование — строки, возвращаемые функциями name() и value(), будут содержать текст, закодированный с использованием той же кодировки, что и исходный файл.»

Если кодировка моего XML — UTF-8, как лучше всего получить возвращаемое значение функции ->value()?

Заранее спасибо.


person Koustav Ghosal    schedule 01.10.2013    source источник
comment
Вы прочитали раздел 1.2 документации, rapidxml.sourceforge.net/? Кажется, что если вы хотите преобразовать UTF-8 в UTF-16, вам придется сделать это самостоятельно. Но это не очень сложно.   -  person john    schedule 01.10.2013
comment
Джон: Пожалуйста, проверьте мою правку   -  person Koustav Ghosal    schedule 01.10.2013
comment
Поскольку вы используете Windows, я думаю, что самым простым способом преобразования UTF-8 в UTF-16 было бы использование функции Windows MultiByteToWideChar. Вы можете найти множество примеров в Интернете по этому поводу.   -  person john    schedule 02.10.2013


Ответы (1)


Помните, что RapidXML — это синтаксический анализатор «на месте»: он анализирует XML и изменяет содержимое, добавляя нулевые терминаторы в нужных местах (и другие вещи).

Таким образом, функция value() на самом деле просто возвращает указатель char * на ваши исходные данные. Если это UTF-8, то RapidXML возвращает указатель на строку символов UTF-8. Другими словами, вы уже делаете то, о чем просили в заголовке вопроса.

Но в опубликованном фрагменте кода вы хотите сохранить wchar_t в структуре. Во-первых, я рекомендую вам вообще этого не делать из-за проблем с владением памятью. Помните, что вы должны использовать C++, а не C. И если вы действительно хотите хранить необработанный указатель, почему бы не использовать тот, который у вас уже есть, в кодировке UTF-8? http://www.utf8everywhere.org/

Но, поскольку это окна, есть (удаленный) шанс, что вам нужно будет передать широкий массив символов в функцию API. Если это так, вам нужно будет преобразовать UTF-8 в широкие символы, используя функцию ОС MultiByteToWideChar

// Get the UTF-8
char *str = xml->first_node("codeSequence")->value();

// work out the size
int size = MultiByteToWideChar(CP_UTF8, 0, str, -1, NULL, 0);

// allocate a vector for that size
std::vector<wchar_t> wide(size);

// do the conversion
MultiByteToWideChar(CP_UTF8, 0, str, -1, &wide[0], size);
person Roddy    schedule 15.10.2013