2010-11-23 3 views
3

Я пытаюсь преобразовать приложение из Java + Swing в C++ + Qt. В какой-то момент мне пришлось иметь дело с некоторыми промежуточными продуктами Unicode. В Java, это было довольно легко:Что именно означает U + и почему я не могу создать таблицу промежуточных строк Unicode в моем приложении на C++?

private static String[] hiraganaTable = { 
    "\u3042", "\u3044", "\u3046", "\u3048", "\u304a", 
    "\u304b", "\u304d", "\u304f", "\u3051", "\u3053", 
    ... 
} 

... в то время как в C++ У меня возникли проблемы:

QString hiraganaTable[] = { 
    "\x30\x42", "\x30\x44", "\x30\x46", "\x30\x48", "\x30\x4a", 
    "\x30\x4b", "\x30\x4d", "\x30\x4f", "\x30\x51", "\x30\x53", 
    ... 
}; 

я не мог использовать \ и в VS2008, потому что я получил кучу предупреждений формы:

символа, представленных универсальным-символьного имя '\ u3042' не может быть представлены в текущей кодовой странице (1250)

И не называйте меня глупым, я попытался использовать File-> Advanced Save Options, но ничего не изменил, кодовая страница вообще не изменилась. Похоже, это известная проблема: How to create a UTF-8 string literal in Visual C++ 2008

В таблице я использую довольно короткий, так и с помощью Vim и некоторых вводного уровня регулярных выражений магии, я был в состоянии преобразовать его в \ x30 \ x42 запись. К сожалению, QStrings не будет правильно инициализироваться с такого ввода. Я все пробовал. fromAscii(), fromUtf8(), fromLocal8Bit(), QString (QByteArray), работает. Затем, пытаясь записать U + 3042 без спецификации в файл, а затем просмотреть его в шестнадцатеричном режиме, я выяснил, что это действительно «E3 81 82». Внезапно запись вроде этого работала с QString :: fromAscii(). Теперь мне осталось интересно, насколько именно «U +» стоит в «U + 3042» (поскольку 0xE38182 - 0x3042 = E35140, может быть, мне лучше добавить эту Волшебную константу ко всем моим будущим символам Unicode?). Как мне исходить отсюда, чтобы получить массив правильных строк UTF-8?

ответ

3

Проблема заключается в том, что C++ базируется на C, которая восходит к ASCII возраста. Строки C по умолчанию «abc» - 8 бит. Ваш компилятор Visual C++ имеет 16-битные Unicode (UTF-16) литералы, хотя и имеет несколько иной синтаксис: L"abc\u3042". Тип таких литералов: wchar_t[N] вместо char[N], вы можете сохранить их в std::wstring.

Qt полностью понимает wchar_t и QStrings могут быть непосредственно построены из них без проблем преобразования.

4

Что вы видите, это кодировка UTF-8 этого символа.

>>> u'\u3042'.encode('utf-8').encode('hex') 
'e38182' 

Если вы пишете их все в UTF-8, тогда все должно быть в порядке.

«U +» просто указывает, что вы просматриваете код Unicode, а не какую-то определенную кодировку.

EDIT:

Небольшой скриптлет, чтобы помочь вам начать работу, в Python (тот же язык, что и выше):

>>> print ',\n'.join(', '.join('"%s"' % (y.encode('utf-8').encode('string-escape') 
     ,) for y in x) for x in [u'あいうえお', u'かきくけこ', u'さしすせそ']) 
"\xe3\x81\x82", "\xe3\x81\x84", "\xe3\x81\x86", "\xe3\x81\x88", "\xe3\x81\x8a", 
"\xe3\x81\x8b", "\xe3\x81\x8d", "\xe3\x81\x8f", "\xe3\x81\x91", "\xe3\x81\x93", 
"\xe3\x81\x95", "\xe3\x81\x97", "\xe3\x81\x99", "\xe3\x81\x9b", "\xe3\x81\x9d" 
2

"U + дддд", где каждый d является шестнадцатеричная цифра обозначает кодовую точку Unicode.

Вы не можете хранить 16-битные значения в 8-битных символах; это основная проблема, с которой вы сталкиваетесь.

Используйте широкие символы, например. (это строковые литералы) L"\0x3042" или L"\u3042".

Затем выясните, как заставить QString принять их.

Примечание: Visual C++ будет издавать глупое предупреждение для нотации \U, используемой в литералах, в то время как g ++ будет издавать глупые слова для этой нотации, используемой за пределами литералов.

Приветствия & НТН.,

+2

На самом деле, кодовые точки Юникода U + PPDDDD, где PP - это шестнадцатеричное значение между 00 и 10 (так, 17 значений), а DDDD - любые четыре шестнадцатеричные цифры. Unicode - это 21-битный набор символов, ** не ** 16-разрядный набор символов. – tchrist 2010-11-24 01:42:11

+0

@tchrist справа, но это лишние детали. в Unicode есть много чего сказать. я мог бы продолжить несколько тысяч страниц. Кстати, о СО. Я отмечаю, что непрактичные, но умные ответы, которые на самом деле не отвечают на вопрос, получают поддержку (в общем). Argh. cheers, – 2010-11-24 01:58:27