Unicode 和多字節字符集 (MBCS) 支持
Visual Studio .NET 2003
有些國際市場以大字符集來使用日文和中文等語言。為了支持這些市場的編程,Microsoft 基礎類庫 (MFC) 支持以兩種方式處理大字符集:
unicode和多字節字符集是兩種不同的編碼方式,不同的編碼方式下,所對應的一些函數是不兼容的。
讀到多字節菜單字符串之后,用MultiByteToWideChar()轉為unicode字符串
或者 使用API的A版本來設置菜單的顯示名稱,比如,SetMenuItemInfoA(...)
如果你新的庫是Unicode的,就用Unicode開發,摒棄多字節編碼,多字節編碼弊端太多了。
其實改起來很簡單,你把所有的char都改成TCHAR,如果能用CString,盡量用CString。所有字符串函數都換上帶_t的版本,比如_tsprintf()、_tcscpy之類的……因為這些東西都是同時兼容Unicode和ANSI的,所以改起來很容易。
你只要對於那些少數的多字節dll函數,參數傳送字符串時實現用WideCharToMultiByte轉換一下。
我們在最開始學習MFC的時候,毫無疑問會遇到這樣的問題。
VC6的設置:多字節。
vs的默認設置:Unicode,在屬性中可以改成多字節。
多字節編碼:char,string,CStringA。
Unicode編碼:wchar_t,wstring,CStringW。
注意:如果項目是Unicode,那么CString就被定義為CStringW,否則就是CStringA。
附:
LPSTR = char*;LPCSTR = const char*;
LPWSTR = wchar_t*;LPCWSTR = const wchar_t*;
至於LPCTSTR也是根據項目字符集來定義為LPCWSTR(Unicode)或LPCSTR(多字節)。
OK,上面的定義很明顯了,注意用的時候別弄混了,我覺得最好的方式是,使用wchar_t和wstring(api大多使用unicode,即使是多字節版本也是把多字節轉成unicode再去調用unicode版api),我不太喜歡CString。
接下來就是轉換:www.2cto.com
// C++
char* 到 string:string str("char"); 或者string str = "char";
string 到 char*:const char* ch = str.c_str();
wchar_t* 和 wstring與上相同。
// MFC
char* 到 CStringA:CStringA str("char");
CStringA 到 char*:const char* ch = str.operator LPCSTR(); (注意:反對使用GetBuffer,因為使用這個,必須要ReleaseBuffer,而且很多時候沒必要去分配空間)
wchar_t* 和 CStringW與上相同。
// 字符集之間轉換
char* 到 wchar_t*:CA2W a2w("char"); const wchar_t* wch = a2w.operator LPCWSTR();
wchar_t* 到 char*:CW2A w2a(L"wchar_t"); const char* ch = w2a.operator LPCSTR(); (注意:反對使用_T("chs")這種方式,程序字符集在一開始就該確定,而且最好選擇Unicode)
關於CA2W和CW2A這兩個類,可以在atlconv.h中找到源代碼,其實就是對WideCharToMultiByte和MultiByteToWideChar的封裝。
http://bbs.esrichina-bj.cn/ESRI/thread-97480-1-1.html
------解決方案--------------------
讀到多字節菜單字符串之后,用MultiByteToWideChar()轉為unicode字符串
或者 使用API的A版本來設置菜單的顯示名稱,比如,SetMenuItemInfoA(...)
------解決方案--------------------
如果你新的庫是Unicode的,就用Unicode開發,摒棄多字節編碼,多字節編碼弊端太多了。
其實改起來很簡單,你把所有的char都改成TCHAR,如果能用CString,盡量用CString。所有字符串函數都換上帶_t的版本,比如_tsprintf()、_tcscpy之類的……因為這些東西都是同時兼容Unicode和ANSI的,所以改起來很容易。
------解決方案--------------------
讀到多字節菜單字符串之后,用MultiByteToWideChar()轉為unicode字符串
或者 使用API的A版本來設置菜單的顯示名稱,比如,SetMenuItemInfoA(...)
------解決方案--------------------
如果你新的庫是Unicode的,就用Unicode開發,摒棄多字節編碼,多字節編碼弊端太多了。
其實改起來很簡單,你把所有的char都改成TCHAR,如果能用CString,盡量用CString。所有字符串函數都換上帶_t的版本,比如_tsprintf()、_tcscpy之類的……因為這些東西都是同時兼容Unicode和ANSI的,所以改起來很容易。
char *str=(LPSTR)(LPCTSTR)strText; //CString轉為Char*
char * ch_a =(char*)str.GetBuffer(str.GetLength());
參考文獻:
https://msdn.microsoft.com/zh-cn/library/cc468203(v=VS.71).aspx
https://msdn.microsoft.com/zh-cn/library/cz0a83sb
ccjt.taobao.com
