UTF-8 в Windows
Вопрос
Как мне установить кодовую страницу на UTF-8 в программе на C Windows? Р>
У меня есть сторонняя библиотека, которая использует fopen для открытия файлов. Я могу использовать wcstombs для преобразования имен файлов Unicode в текущую кодовую страницу, однако, если у пользователя есть имя файла с символом вне кодовой страницы, это нарушается. Р>
В идеале я бы просто позвонил _setmbcp (65001), чтобы установить кодовую страницу в UTF-8, однако в документации MSDN для _setmbcp говорится, что UTF-8 не поддерживается. Р>
Как я могу обойти это?
Решение
К сожалению, нет способа сделать Unicode текущей кодовой страницей в Windows. Константы CP_UTF7
и CP_UTF8
являются псевдо-кодовыми страницами, используемыми только в MultiByteToWideChar и WideCharToMultiByte - функции преобразования, как упоминал Бен.
Ваша проблема похожа на проблему классов Fstream C ++. Конструкторы fstream принимают только имена char *
, что делает невозможным открытие файла с истинным именем Unicode. Единственное решение, предлагаемое VC, - это хак: открыть файл отдельно, а затем установить дескриптор объекта потока. Я боюсь, что это не вариант для вас, конечно, поскольку сторонняя библиотека, вероятно, не принимает дескрипторы.
Единственное решение, которое я могу придумать, - это создать временный файл с именем, отличным от Unicode, который жестко связан с оригиналом, и использовать его в качестве параметра.
Другие советы
Все API-интерфейсы Windows думают в UTF-16, поэтому вам лучше написать оболочку для вашей библиотеки, которая преобразует границы. Р>
Как ни странно, Windows считает UTF-8 кодовой страницей для целей преобразования, поэтому вы используете те же API, что и для преобразования между кодовыми страницами:
std::wstring Utf8ToUtf16(const char* u8string)
{
int wcharcount = strlen(u8string);
wchar_t *tempWstr = new wchar_t[wcharcount];
MultiByteToWideChar(CP_UTF8, 0, u8string, -1, tempWstr, wcharcount);
wstring w(tempWstr);
delete [] tempWstr;
return w;
}
И что-то похожее по форме для преобразования обратно.
Обновление 2018 года: Windows 10 сделала " 65001 " кодовая страница меньше "псевдо" в два этапа:
<Ол> Изменения conhost
: Подсистема Windows для Linux использует кодовую страницу 65001 для своих консолей. Также возможно запустить chcp 65001
в cmd.exe
после WSL. (Это вызвало некоторые довольно глупые ошибки Python .) Используйте cygwin (который по умолчанию предоставляет языковой стандарт UTF-8) или напишите свой собственный взлом libc для Windows, который выполняет необходимые переводы с UTF-8 в UTF-16 и переносит нестандартные _wfopen
и т. д. . функции.