Windows WCHAR 到 Linux wchar_t 字符类型的转换

来源:互联网 发布:linux视频教程百度网盘 编辑:程序博客网 时间:2024/05/18 03:08

1、简介
这几天涉及到一个小项目,Windows 和Linux通过TCP进行通信,但是他们之间的字符类型上是有区别的,所有Windows上的数据发送到Linux上后,如果不经过转换,会出现乱码的情况,Windows 的WCHAR类型实际上是wchar_t,但是它只占用2个字节(既UTF-16),而Linux上wchar_t则使用的是多字节(UTF-8),下面的函数提供了他们之间的相互转换!

2、程序代码

#ifdef WINDOWS#include <windows.h>#include <stdio.h>#include <ctype.h>#else#include <wchar.h>#include <string.h>#endif#ifdef WIN32#define USES_WCSUTF16_CONV#define WCS2UTF16(wcs) (wcs)#define UTF162WCS(utf16) (utf16)#else //WIN32//wchar_t to char16_tunsigned short * _wcsu16_wcs2utf16(wchar_t *wcs, unsigned short * utf16, int len){    int wc;    wchar_t *end = wcs + len;    unsigned short * ret = utf16;    while(wcs < end)    {        wc = *(wcs++);        if (wc > 0xFFFF)        {            wc -= 0x00010000L;            *utf16++ = 0xD800 | (wc >> 10);            *utf16++ = 0xDC00 | (wc & 0x03FF);        }        else        {            *utf16++ = wc;        }    }    return ret;}//wchar_t lengthint _wcsu16_utf16len(wchar_t *wcs){    int wc;    int ret = 0;    while(wc = *wcs++)        ret += wc > 0xFFFF ? 2 : 1;    return ret;}//char16_t lengthint _wcsu16_wcslen(unsigned short * utf16){    unsigned short * start = utf16;    while(*utf16++) ;    return (int)(utf16 - start - 1);}//char16_t to wchar_twchar_t * _wcsu16_utf162wcs(unsigned short * utf16, wchar_t *wcs, int len){    if (sizeof(unsigned short) == sizeof(wchar_t))    {        memcpy(wcs, utf16, (len + 1) * sizeof(wchar_t));        return wcs;    }    else    {        int u32;        unsigned short *end = utf16 + len;        wchar_t * ret = wcs;        int u32low = 0;        while (utf16 < end)        {            u32 = *utf16++;            if (u32>=0xD800 && u32<0xDC00)            {                u32low  = *utf16++;                u32   &=  0x3FF;                u32low  &=  0x3FF;                u32   <<= 10;                u32   +=  u32low;                u32   +=  0x10000;            }            *wcs++ = u32;        }        *(wcs-1) = 0;        return ret;    }}#define USES_WCSUTF16_CONV int _len; (_len);  wchar_t * _wcs; (_wcs); unsigned short * _utf16; (_utf16)#define WCS2UTF16(wcs) \(((_wcs = wcs) == NULL) ? NULL : (\                                 _len = (_wcsu16_utf16len(_wcs)+1),\                                 _wcsu16_wcs2utf16(_wcs, (unsigned short *) alloca(_len*2), _len)))#define UTF162WCS(utf16) \(((_utf16 = utf16) == NULL) ? NULL : (\                                _len = (_wcsu16_wcslen(_utf16)+1),\                                _wcsu16_utf162wcs(_utf16, (wchar_t *) alloca(_len*sizeof(wchar_t)), _len)))#endif  //WIN32

3、附加说明
Linux下表示Windows下的16位的wchar_t类型可使用unsigned short来表示,也可直接使用C++中的char16_t类型

0 0
原创粉丝点击