UTF-8 >> Win-1251

Тема в разделе "WASM.WIN32", создана пользователем EvgA, 1 сен 2004.

  1. EvgA

    EvgA New Member

    Публикаций:
    0
    Регистрация:
    5 июл 2004
    Сообщения:
    5
    Адрес:
    Kazakhstan
    Доброе время суток.



    Кто знает как можно перевести строку с UTF-8 в Win-1251, перелапатил MSDN но ничего так и не нашел :dntknw: У кого есть соображения на эту тему сообщите плз, должны же быть какието функции по переводу с одной кодировки в др.
     
  2. reverser

    reverser New Member

    Публикаций:
    0
    Регистрация:
    27 янв 2004
    Сообщения:
    615
    MultiByteToWideChar(CP_UTF8,...);

    WideCharToMultiByte(1251,...);

    В принципе первый шаг (UTF-8 -> UTF-16) можно и ручками, это не очень сложно...
     
  3. masquer

    masquer wasm.ru

    Публикаций:
    0
    Регистрация:
    13 сен 2002
    Сообщения:
    890
    Адрес:
    Николаев
    что это за ахинея?
     
  4. SmikeX

    SmikeX New Member

    Публикаций:
    0
    Регистрация:
    5 июн 2003
    Сообщения:
    20
    если это кириллица, то, согласно определению UTF-8,
    это все равно, что и UTF-16, т к 2 байта на символ
    для сомневающихся см.
    http://en.wikipedia.org/wiki/UTF-8
    http://en.wikipedia.org/wiki/UTF-16

    предcтавленный reverser,oм вариант с
    WideCharToMultiByte(1251,...);
    работает, для всех буковок Win-1251, кроме Ё/ё
    (в win-1251 коды соответственно 0xa8 и 0xb8,
    в UNICODE - 0x410 и 0x451).
    WideCharToMultiByte ковертирует 0xa8 в 0x415 (что еще приемлемо),
    а вот 0xb8 в 0x308!

    поэтому, когда мне потребовался собственный кирилличный редактор,
    а это нужно, если в России только числишься, а практически не живешь,
    я написал свой и поэкспериментировал с немного
    http://russiantext.ircdb.org/ruseditE.htm
    Редактор собственные функции перекодировок, в том числе из Win-1251 в Unicode,
    которой готов поделится. Все очень просто, т к алфавитный порядок в
    Кириллице для Unicode и Win-1251 совпадает с инкриментом кодов,
    опять же кроме буковок Ё/ё. С koi-8 сложнее, т к там алфавитный порядок
    идет в разброс с кодировкой (хотя koi-8 имеет другие свои прелести).
    В то же время, согласен, что усеченные кодовые таблицы win-1251 упукают
    Ё/ё (также как это делает и WideCharToMultiByte), однако под эти символы в win-1251
    забиты реальные коды
    см.
    http://ru.wikipedia.org/wiki/Windows-1251
    Код (Text):
    1. WORD ConvertWin1251ToUnicode(BYTE byCode)
    2. {
    3.    WORD wCode;
    4.    if(byCode<0xC0)
    5.    {
    6.       switch(byCode)
    7.       {
    8.       case 0xa8:
    9.          wCode = 0x401;
    10.          break;
    11.       case 0xb8:
    12.          wCode = 0x451;
    13.          break;
    14.       default:
    15.          wCode = byCode;
    16.          break;
    17.       }
    18.    } else {
    19.       wCode = 0x410 + (WORD)(byCode - 0xc0);
    20.    }
    21.    return wCode;
    22. }
     
  5. Asterix

    Asterix New Member

    Публикаций:
    0
    Регистрация:
    25 фев 2003
    Сообщения:
    3.576
    кусок скрипта mIRC'а =)
     
  6. IceStudent

    IceStudent Active Member

    Публикаций:
    0
    Регистрация:
    2 окт 2003
    Сообщения:
    4.300
    Адрес:
    Ukraine
    Разве? Что-то мне подсказывает, что он работает для всех буковок..
     
  7. SmikeX

    SmikeX New Member

    Публикаций:
    0
    Регистрация:
    5 июн 2003
    Сообщения:
    20
    мне моя совесть подсказывает обратное,
    и подсказка основана на эксперименте

    засомневался, однако, и решил повторить
    вот пример кода

    Код (Text):
    1. char sz1251[] =  {0xc0,0xc1,0xc2,0xa8,0xb8};
    2. WORD szUni[6];
    3. int nError = MultiByteToWideChar(1251,MB_COMPOSITE,
    4.           sz1251, 5, szUni,5);
    5. printf("%X,%X,%X,%X,%X. Error %d", szUni[0], szUni[1], szUni[2], szUni[3], szUni[4], nError);
    выдает
    410,411,412,415,308. Error=0
    должно быть
    410,411,412,401,451. Error=5

    кстати если исключить 0xa и 0xb8, заменив их на 0xc3,0xc4
    функция пашет нормально

    410,411,412,413,414. Error=5

    экспериментировал на американской XP Prof, кто знает, может на русской
    kernel32.dll c MultiByteToWideChar слегка подправлен.
    Ho сожалению проверить не могу, если есть Russian XP или какой другой Russian Windows
    попробуй
     
  8. IceStudent

    IceStudent Active Member

    Публикаций:
    0
    Регистрация:
    2 окт 2003
    Сообщения:
    4.300
    Адрес:
    Ukraine
    SmikeX
    Ты бы лучше основывался на отладчике:
    Код (Text):
    1.     char sz1251[] =  {0xc0,0xc1,0xc2,0xa8,0xb8};
    2.     wchar_t szUni[10];
    3.  
    4.     SetLastError(0);
    5.     int nLen = MultiByteToWideChar(1251,MB_COMPOSITE,sz1251, 5, szUni,5);
    6.     printf("%X,%X,%X,%X,%X. len %d, err: 0x%X\n", szUni[0], szUni[1], szUni[2], szUni[3], szUni[4], nLen, GetLastError());
    7.  
    8.     SetLastError(0);
    9.     nLen = MultiByteToWideChar(1251,MB_COMPOSITE,sz1251, 5, szUni,10);
    10.     printf("%X,%X,%X,%X,%X. len %d, err: 0x%X\n", szUni[0], szUni[1], szUni[2], szUni[3], szUni[4], nLen, GetLastError());
    11.  
    12.     SetLastError(0);
    13.     nLen = MultiByteToWideChar(1251,0,sz1251, 5, szUni,5);
    14.     printf("%X,%X,%X,%X,%X. len %d, err: 0x%X\n", szUni[0], szUni[1], szUni[2], szUni[3], szUni[4], nLen, GetLastError());
    Так даже нагляднее.
     
  9. SmikeX

    SmikeX New Member

    Публикаций:
    0
    Регистрация:
    5 июн 2003
    Сообщения:
    20
    Спасибо, IceStudent, действительно, MultiByteToWideChar работает
    с некоторыми значениями флагов, в частности, с MB_PRECOMPOSED