C语言中的宽字符
寬字符庫函數 我們都知道如何找出一個字符串的長度。例如,如果我們定義了一個指向字符串的指針:
char * pc = "Hello!";我們可以調用
iLength = strlen(pc);變量iLength會被設成6,也就是字符串中字符的個數。 好極了!現在讓我們嘗試定義一個指向寬字符串的指針:
wchar_t * pw = L"Hello!";而且現在我們再次調用strlen:
iLength = strlen(pw);現在問題出現了。首先,C編譯器會給你一個警告消息,大概是下面這個意思:
'function' : incompatible types - from 'unsigned short *' to 'const char *'這是在告訴你strlen函數被定義為接受一個指向char的指針,但這里收到的是一個指向無符號短整型的指針。仍然可以編譯運行程序,但你會發現iLength變成了1。發生了什么呢? 字符串"Hello!"中的6個字符包含的16位值如下:
0x0048 0x0065 0x006C 0x006C 0x006F 0x0021這些值被Intel處理器以下面這種方式存儲在內存中:
48 00 65 00 6C 00 6C 00 6F 00 21 00strlen函數,假設它試圖找到字符串的長度,計算第一個字節為字符,但然后會認為第二字節是一個表明字符串結尾的零字節。 這個小小的實驗清楚地表明了C語言自身和運行庫函數的細微差別。編譯器將字符串L"Hello! "解釋為一個16位短整型的集合并把它們存儲在wchar_t數組。編譯器還會處理所有數組索引和sizeof操作符,因此這些都會正常工作。但是,程序運行時,運行庫函數(如strlen)是在鏈接時被增加進去的。這些函數期望收到由單字節字符構成的字符串。因此在遇到寬字符串時,它們不會像我們預期那樣執行。 你說,哦,太倒霉了,現在每一個C庫函數都要被重寫,以接受寬字符。嗯,并非每一個C庫函數。只有那些有字符串參數的。而且你并不需要重寫它們,因為重寫已經完成了。 寬字符版本的strlen函數被稱為wcslen("寬字符字符串長度"),并定義在STRING.H(也就是strlen被定義的地方)和WCHAR.H中。strlen函數的聲明如下:
size_t __cdecl strlen(const char*);而wcslen函數的聲明如下:
size_t __cdecl wcslen(const wchar_t*);所以現在我們知道了一點:在需要確定一個寬字符串的長度時,我們可以調用以下函數:
iLength = wcslen(pw);該函數返回的結果是6,也就是字符串中的字符個數。
請記住,在使用寬字符的時候,字符串的字符長度并沒有改變,改變的只是字節長度。
所有你喜愛的C語言中那些使用字符串參數的運行庫函數都有寬字符的版本。
例如,wprintf是寬字符版本的printf。這些函數都被定義在WCHAR.H和定義正常函數的頭文件中。
轉載于:https://www.cnblogs.com/trying/archive/2012/07/16/2863761.html
總結
- 上一篇: poj2318 TOYS
- 下一篇: POJ 3750 小孩报数问题