在開發文檔編輯器經常會遇到各種編碼轉換的問題要解決,雖然windows api有相關的函數。但是參數多,使用復雜每次都要查手冊,很容易出錯。
所以把常用的轉換封裝一下,用C的語法實現。支持c/c++
注意這些函數都會在堆中創建并返回新的字串,所以返回的字符串在使用完以后要顯示銷毀使用free(xxx)否則會造成內存泄漏。
第一條宏是取消煩人的VS編譯器強制要求使用xxx_s函數的宏。如果在非VS編譯器下會被自動忽略。
[cpp] view plain
copy print?
#define?_CRT_SECURE_NO_WARNINGS??#include?<stdio.h>????#include?<windows.h>????#include?<locale.h>????#define?BUFF_SIZE?1024??????wchar_t?*?ANSIToUnicode(const?char*?str)??{??????int?textlen;??????wchar_t?*?result;??????textlen?=?MultiByteToWideChar(CP_ACP,?0,?str,?-1,?NULL,?0);??????result?=?(wchar_t?*)malloc((textlen?+?1)*sizeof(wchar_t));??????memset(result,?0,?(textlen?+?1)*sizeof(wchar_t));??????MultiByteToWideChar(CP_ACP,?0,?str,?-1,?(LPWSTR)result,?textlen);??????return?result;??}????char?*?UnicodeToANSI(const?wchar_t*?str)??{??????char*?result;??????int?textlen;??????textlen?=?WideCharToMultiByte(CP_ACP,?0,?str,?-1,?NULL,?0,?NULL,?NULL);??????result?=?(char?*)malloc((textlen?+?1)*sizeof(char));??????memset(result,?0,?sizeof(char)?*?(textlen?+?1));??????WideCharToMultiByte(CP_ACP,?0,?str,?-1,?result,?textlen,?NULL,?NULL);??????return?result;??}????wchar_t?*?UTF8ToUnicode(const?char*?str)??{??????int?textlen;??????wchar_t?*?result;??????textlen?=?MultiByteToWideChar(CP_UTF8,?0,?str,?-1,?NULL,?0);??????result?=?(wchar_t?*)malloc((textlen?+?1)*sizeof(wchar_t));??????memset(result,?0,?(textlen?+?1)*sizeof(wchar_t));??????MultiByteToWideChar(CP_UTF8,?0,?str,?-1,?(LPWSTR)result,?textlen);??????return?result;??}????char?*?UnicodeToUTF8(const?wchar_t*?str)??{??????char*?result;??????int?textlen;??????textlen?=?WideCharToMultiByte(CP_UTF8,?0,?str,?-1,?NULL,?0,?NULL,?NULL);??????result?=?(char?*)malloc((textlen?+?1)*sizeof(char));??????memset(result,?0,?sizeof(char)?*?(textlen?+?1));??????WideCharToMultiByte(CP_UTF8,?0,?str,?-1,?result,?textlen,?NULL,?NULL);??????return?result;??}????char*?w2m(const?wchar_t*?wcs)??{??????int?len;??????char*?buf;??????len?=?wcstombs(NULL,?wcs,?0);??????if?(len?==?0)??????????return?NULL;??????buf?=?(char?*)malloc(sizeof(char)*(len?+?1));??????memset(buf,?0,?sizeof(char)?*(len?+?1));??????len?=?wcstombs(buf,?wcs,?len?+?1);??????return?buf;??}????wchar_t*?m2w(const?char*?mbs)??{??????int?len;??????wchar_t*?buf;??????len?=?mbstowcs(NULL,?mbs,?0);??????if?(len?==?0)??????????return?NULL;??????buf?=?(wchar_t?*)malloc(sizeof(wchar_t)*(len?+?1));??????memset(buf,?0,?sizeof(wchar_t)?*(len?+?1));??????len?=?mbstowcs(buf,?mbs,?len?+?1);??????return?buf;??}????char*?ANSIToUTF8(const?char*?str)??{??????wchar_t?*?buf?=?ANSIToUnicode(str);??????char?*?ret?=??UnicodeToUTF8(buf);??????free(buf);??????return?ret;??}????char*?UTF8ToANSI(const?char*?str)??{??????wchar_t?*?buf?=?UTF8ToUnicode(str);??????char?*?ret?=?UnicodeToANSI(buf);??????free(buf);??????return?ret;??}????int?main()??{??????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????char?str[]?=?"多選控件";??????char?*?buf?=?ANSIToUTF8(str);??????BYTE?pbuf[255];??????memcpy(pbuf,?buf,?strlen(buf)?+?1);??????int?i?=?0;??????char?outbuff[BUFF_SIZE];??????FILE*?????outfile?=?fopen("out.txt",?"wb");??????while?(pbuf[i])??????{??????????sprintf(outbuff,?"0x%02x,?",?pbuf[i++]);??????????fputs(outbuff,?outfile);??????}??????sprintf(outbuff,?"0x00}");??????fputs(outbuff,?outfile);??????fclose(outfile);????????free(buf);??????return?0;??}??
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <windows.h>
#include <locale.h>
#define BUFF_SIZE 1024 wchar_t * ANSIToUnicode(const char* str)
{int textlen;wchar_t * result;textlen = MultiByteToWideChar(CP_ACP, 0, str, -1, NULL, 0);result = (wchar_t *)malloc((textlen + 1)*sizeof(wchar_t));memset(result, 0, (textlen + 1)*sizeof(wchar_t));MultiByteToWideChar(CP_ACP, 0, str, -1, (LPWSTR)result, textlen);return result;
}char * UnicodeToANSI(const wchar_t* str)
{char* result;int textlen;textlen = WideCharToMultiByte(CP_ACP, 0, str, -1, NULL, 0, NULL, NULL);result = (char *)malloc((textlen + 1)*sizeof(char));memset(result, 0, sizeof(char) * (textlen + 1));WideCharToMultiByte(CP_ACP, 0, str, -1, result, textlen, NULL, NULL);return result;
}wchar_t * UTF8ToUnicode(const char* str)
{int textlen;wchar_t * result;textlen = MultiByteToWideChar(CP_UTF8, 0, str, -1, NULL, 0);result = (wchar_t *)malloc((textlen + 1)*sizeof(wchar_t));memset(result, 0, (textlen + 1)*sizeof(wchar_t));MultiByteToWideChar(CP_UTF8, 0, str, -1, (LPWSTR)result, textlen);return result;
}char * UnicodeToUTF8(const wchar_t* str)
{char* result;int textlen;textlen = WideCharToMultiByte(CP_UTF8, 0, str, -1, NULL, 0, NULL, NULL);result = (char *)malloc((textlen + 1)*sizeof(char));memset(result, 0, sizeof(char) * (textlen + 1));WideCharToMultiByte(CP_UTF8, 0, str, -1, result, textlen, NULL, NULL);return result;
}
/*寬字符轉換為多字符Unicode - ANSI*/
char* w2m(const wchar_t* wcs)
{int len;char* buf;len = wcstombs(NULL, wcs, 0);if (len == 0)return NULL;buf = (char *)malloc(sizeof(char)*(len + 1));memset(buf, 0, sizeof(char) *(len + 1));len = wcstombs(buf, wcs, len + 1);return buf;
}
/*多字符轉換為寬字符ANSI - Unicode*/
wchar_t* m2w(const char* mbs)
{int len;wchar_t* buf;len = mbstowcs(NULL, mbs, 0);if (len == 0)return NULL;buf = (wchar_t *)malloc(sizeof(wchar_t)*(len + 1));memset(buf, 0, sizeof(wchar_t) *(len + 1));len = mbstowcs(buf, mbs, len + 1);return buf;
}char* ANSIToUTF8(const char* str)
{wchar_t * buf = ANSIToUnicode(str);char * ret = UnicodeToUTF8(buf);free(buf);return ret;
}char* UTF8ToANSI(const char* str)
{wchar_t * buf = UTF8ToUnicode(str);char * ret = UnicodeToANSI(buf);free(buf);return ret;
}int main()
{///*使用wcstombs和mbstowcs之前必須調用setlocale,以便決定內碼*///setlocale(LC_ALL, ".936");///*假定有一個Unicode(UTF-16LE)編碼的文件,將其打開,重新編碼為ANSI,寫入aa.txt中,再繼續編碼回Unicode,寫入aw.txt中*////*如果不存在a.txt文件,則程序出錯,沒有做錯誤處理*///char* filename = "a.txt";//char* filenamea = "aa.txt";//char* filenamew = "aw.txt";//FILE* input = fopen(filename, "rb");//FILE* inputa = fopen(filenamea, "wb");//FILE* inputw = fopen(filenamew, "wb");//wchar_t * buf;///*BOE設置,UTF-16LE的BOE為FEFF,如果不先將其讀取出來,wcstombs會調用失敗*///fgetwc(input);//fputwc(0xFEFF, inputw);///*開始讀取文件*///while (!feof(input))//{// buf = (wchar_t *)malloc(sizeof(wchar_t)*BUFF_SIZE);// memset(buf, 0, sizeof(wchar_t) * BUFF_SIZE);// fgetws(buf, BUFF_SIZE, input);// fputs(w2m(buf), inputa);// fputws(m2w(w2m(buf)), inputw);//}///*后續處理*///fclose(input);//fclose(inputa);//fclose(inputw);//free(buf);char str[] = "多選控件";char * buf = ANSIToUTF8(str);BYTE pbuf[255];memcpy(pbuf, buf, strlen(buf) + 1);int i = 0;char outbuff[BUFF_SIZE];FILE* outfile = fopen("out.txt", "wb");while (pbuf[i]){sprintf(outbuff, "0x%02x, ", pbuf[i++]);fputs(outbuff, outfile);}sprintf(outbuff, "0x00}");fputs(outbuff, outfile);fclose(outfile);free(buf);return 0;
}
總結
以上是生活随笔為你收集整理的一套Windows上C/C++的编码转换函数的全部內容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。