宽字符wchar、窄字符char、无符号字符(unsigned char)之间的转换

原创 2016年08月30日 19:23:18


头文件:

  

 typedef char                                        str_ansi;
 typedef unsigned char                               str_utf8;
 typedef wchar_t                                     str_utf16;

class CAPECharacterHelper
{
public:
    static str_ansi * GetANSIFromUTF8(const str_utf8 * pUTF8);
    static str_ansi * GetANSIFromUTF16(const str_utf16 * pUTF16);
    static str_utf16 * GetUTF16FromANSI(const str_ansi * pANSI);
    static str_utf16 * GetUTF16FromUTF8(const str_utf8 * pUTF8);
    static str_utf8 * GetUTF8FromANSI(const str_ansi * pANSI);
    static str_utf8 * GetUTF8FromUTF16(const str_utf16 * pUTF16);
};

源文件:

 

str_ansi * CAPECharacterHelper::GetANSIFromUTF8(const str_utf8 * pUTF8)
{
    str_utf16 * pUTF16 = GetUTF16FromUTF8(pUTF8);
    str_ansi * pANSI = GetANSIFromUTF16(pUTF16);
    delete [] pUTF16;
    return pANSI;
}

str_ansi * CAPECharacterHelper::GetANSIFromUTF16(const str_utf16 * pUTF16)
{
    const int nCharacters = pUTF16 ? int(wcslen(pUTF16)) : 0;
    #ifdef _WIN32
        int nANSICharacters = (2 * nCharacters);
        str_ansi * pANSI = new str_ansi [nANSICharacters + 1];
        memset(pANSI, 0, (nANSICharacters + 1) * sizeof(str_ansi));
        if (pUTF16)
            WideCharToMultiByte(CP_ACP, 0, pUTF16, -1, pANSI, nANSICharacters, NULL, NULL);
    #else
        str_utf8 * pANSI = new str_utf8 [nCharacters + 1];
        for (int z = 0; z < nCharacters; z++)
            pANSI[z] = (pUTF16[z] >= 256) ? '?' : (str_utf8) pUTF16[z];
        pANSI[nCharacters] = 0;
    #endif

    return (str_ansi *) pANSI;
}

str_utf16 * CAPECharacterHelper::GetUTF16FromANSI(const str_ansi * pANSI)
{
    const int nCharacters = pANSI ? int(strlen(pANSI)) : 0;
    str_utf16 * pUTF16 = new str_utf16 [nCharacters + 1];

    #ifdef _WIN32
        memset(pUTF16, 0, sizeof(str_utf16) * (nCharacters + 1));
        if (pANSI)
            MultiByteToWideChar(CP_ACP, 0, pANSI, -1, pUTF16, nCharacters);
    #else
        for (int z = 0; z < nCharacters; z++)
            pUTF16[z] = (str_utf16) ((str_utf8) pANSI[z]);
        pUTF16[nCharacters] = 0;
    #endif

    return pUTF16;
}

str_utf16 * CAPECharacterHelper::GetUTF16FromUTF8(const str_utf8 * pUTF8)
{
    // get the length
    int nCharacters = 0; int nIndex = 0;
    while (pUTF8[nIndex] != 0)
    {
        if ((pUTF8[nIndex] & 0x80) == 0)
            nIndex += 1;
        else if ((pUTF8[nIndex] & 0xE0) == 0xE0)
            nIndex += 3;
        else
            nIndex += 2;

        nCharacters += 1;
    }

    // make a UTF-16 string
    str_utf16 * pUTF16 = new str_utf16 [nCharacters + 1];
    nIndex = 0; nCharacters = 0;
    while (pUTF8[nIndex] != 0)
    {
        if ((pUTF8[nIndex] & 0x80) == 0)
        {
            pUTF16[nCharacters] = pUTF8[nIndex];
            nIndex += 1;
        }
        else if ((pUTF8[nIndex] & 0xE0) == 0xE0)
        {
            pUTF16[nCharacters] = ((pUTF8[nIndex] & 0x1F) << 12) | ((pUTF8[nIndex + 1] & 0x3F) << 6) | (pUTF8[nIndex + 2] & 0x3F);
            nIndex += 3;
        }
        else
        {
            pUTF16[nCharacters] = ((pUTF8[nIndex] & 0x3F) << 6) | (pUTF8[nIndex + 1] & 0x3F);
            nIndex += 2;
        }

        nCharacters += 1;
    }
    pUTF16[nCharacters] = 0;

    return pUTF16; 
}

str_utf8 * CAPECharacterHelper::GetUTF8FromANSI(const str_ansi * pANSI)
{
    str_utf16 * pUTF16 = GetUTF16FromANSI(pANSI);
    str_utf8 * pUTF8 = GetUTF8FromUTF16(pUTF16);
    delete [] pUTF16;
    return pUTF8;
}

str_utf8 * CAPECharacterHelper::GetUTF8FromUTF16(const str_utf16 * pUTF16)
{
    // get the size(s)
    int nCharacters = int(wcslen(pUTF16));
    int nUTF8Bytes = 0;
    for (int z = 0; z < nCharacters; z++)
    {
        if (pUTF16[z] < 0x0080)
            nUTF8Bytes += 1;
        else if (pUTF16[z] < 0x0800)
            nUTF8Bytes += 2;
        else
            nUTF8Bytes += 3;
    }

    // allocate a UTF-8 string
    str_utf8 * pUTF8 = new str_utf8 [nUTF8Bytes + 1];

    // create the UTF-8 string
    int nUTF8Index = 0;
    for (int z = 0; z < nCharacters; z++)
    {
        if (pUTF16[z] < 0x0080)
        {
            pUTF8[nUTF8Index++] = (str_utf8) pUTF16[z];
        }
        else if (pUTF16[z] < 0x0800)
        {
            pUTF8[nUTF8Index++] = 0xC0 | (pUTF16[z] >> 6);
            pUTF8[nUTF8Index++] = 0x80 | (pUTF16[z] & 0x3F);
        }
        else
        {
            pUTF8[nUTF8Index++] = 0xE0 | (pUTF16[z] >> 12);
            pUTF8[nUTF8Index++] = 0x80 | ((pUTF16[z] >> 6) & 0x3F);
            pUTF8[nUTF8Index++] = 0x80 | (pUTF16[z] & 0x3F);
        }
    }
    pUTF8[nUTF8Index++] = 0;

    // return the UTF-8 string
    return pUTF8;
}

请注意,该转换函数中有开辟空间(new)而没有空间删除,在调用这些函数的时候注意在外面delete

char*与wchar_t*(LPTSTR) 如何相互转换

#include//标准C++; string   tp;  wchar_t   *s;  char   *d;  tp=s;  d=tp.c_str();  也可使用WideChar...
  • zang141588761
  • zang141588761
  • 2015年10月28日 10:17
  • 3467

C语言char*字符串数组和unsigned char[]数组的相互转换

#include #include using namespace std; void convertUnCharToStr(char* str, unsigned char* UnChar, ...
  • u010312436
  • u010312436
  • 2016年06月08日 21:36
  • 14273

该使用char还是unsigned char

这个问题似乎很简单,要表示8位无符号数值的时候,用unsigned char,要表示8位有符号数值或者ASCII字符的时候,用char。但是,有的时候会遇到这样一种情况,从一串字符串中取出的字符,既有...
  • lfw19891101
  • lfw19891101
  • 2011年07月25日 11:29
  • 7200

C++之char , signed char , unsigned char(转)

ANSI C 提供了3种字符类型,分别是char、signed char、unsigned char.而不是像short、int一样只有两种(int默认就是unsigned int). 三者都占1个...
  • dragoo1
  • dragoo1
  • 2013年04月22日 09:53
  • 1247

C语言unsigned char、char与int之间的转换

参考博客:点击打开链接
  • bladeandmaster88
  • bladeandmaster88
  • 2016年10月23日 18:40
  • 4318

char和unsigned char强制转换成int后的差异

最近有人提到char和unsigned char有什么区别,当然这个问题如果刚学计算机或者编程语言的人来说,非常简单。我也这么认为,无非就是有符号和无符号的差别嘛。 这个问题让我想到了以前学...
  • lida2003
  • lida2003
  • 2011年11月16日 21:30
  • 14779

C/C++ 十六进制char*与Binary char*相互转换

1. 十六进制char* 转 Binary char*例如:“fedcba9876543210” 转换为:char bin[8] ={0xfe,0xdc,0xba,0x98,0x76,0x54,0x...
  • Jeanphorn
  • Jeanphorn
  • 2015年05月07日 14:32
  • 6511

如何把char str,或unsigned char str转换成CString

  • 2012年09月24日 17:34
  • 22KB
  • 下载

宽字符和窄字符之间的转换

经常会用到,保存在这里以便直接拿去用~ // 窄字符串转化为宽字符串,结果数据保存到第二个参数中,因此要在调用函数之前申请好空间 // BOOL WINAPI Ansi2Unicode(__in ...
  • CoderAldrich
  • CoderAldrich
  • 2016年12月15日 10:56
  • 1788

C++ 窄字符转换为宽字符

wstring A2W(const string &s) { const char * szSource = s.c_str(); size_t _Dsize = MultiByteT...
  • ming2453755227
  • ming2453755227
  • 2016年08月09日 16:26
  • 271
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:宽字符wchar、窄字符char、无符号字符(unsigned char)之间的转换
举报原因:
原因补充:

(最多只允许输入30个字)