2017-05-26 29 views
0

我試圖測試超出BMP範圍的Unicode。下面我使用+ UD834DF01作爲示例字符,並嘗試將其轉換爲多字節字符,但程序失敗並說'非法字節序列',爲什麼?wctomb失敗:非法字節序列

#include <stdio.h> 
#include <wchar.h> 
#include <locale.h> 
#include <stdlib.h> 
#include <limits.h> 

int main(int argc, const char *argv[]) 
{ 
    setlocale(LC_ALL, ""); // my locale is UTF-8 

    wchar_t wc = 0xd834df01; 
    char bytes[MB_LEN_MAX] = {0}; 
    int r = wctomb(bytes, wc); 
    if (r > 0) { 
     for (int i = 0; i < MB_LEN_MAX; i++) 
      printf("0x%x\n", bytes[i]); 
    } else { 
     perror("fail"); 
    } 

    return 0; 
} 

回答

1

Hex D834DF01不是有效的Unicode碼點;沒有超過十六進制110000的值。 「替代」代碼單元D834和DF01的(的序列)是UTF-16編碼碼點U + 10D301是在一個私用區域,而不是一個標準字符,而是有效地編碼以UTF-8作爲f4 8d 8c 81. UTF-16用於Windows的大部分,幾乎所有的Java和其他一些地方。

更正:我在我腦子裏進行了代理轉換,並滑倒了一個hexit;作爲評論,它實際上是在Tai Xuan Jing的U + 1D301 digram for heavenly earth

+0

這就是說gcc使用wchar_t來表示一個Unicode代碼點嗎? – noinput

+0

我試過libiconv,但是我的結果是U + 01D301和UTF-8作爲0xf0 0x9d 0x8c 0x81 – noinput

+0

@noinput:寬字符/字符串支持主要是你的C庫而不是你的編譯器,glibc是現代的Unicode即UCS- 4。你對1D301是正確的,請參閱編輯。 –