Vc下unicode和UTF8相互转换
在vc下使用SQLite数据库时,由于SQL语句使用utf8 编码,而CString 是unicode编码。
一, utf8 转 Unicode
CString UTF8ToUnicode(char* UTF8)
{
    DWORD dwUnicodeLen;        //转换后Unicode的长度
    TCHAR *pwText;            //保存Unicode的指针
    CString strUnicode;        //返回值
    //获得转换后的长度,并分配内存
    dwUnicodeLen = MultiByteToWideChar(CP_UTF8,0,UTF8,-1,NULL,0);
    pwText = new TCHAR[dwUnicodeLen];
    if (!pwText)
    {
        return strUnicode;
    }
    //转为Unicode
    MultiByteToWideChar(CP_UTF8,0,UTF8,-1,pwText,dwUnicodeLen);
    //转为CString
    strUnicode.Format(_T("%s"),pwText);
    //清除内存
    delete []pwText;
    //返回转换好的Unicode字串
    return strUnicode;
}
二, Unicode转utf8
size_t CDGQDialog::g_f_wctou8(char * dest_str, const wchar_t src_wchar)
{
    int count_bytes = 0;
    wchar_t byte_one = 0, byte_other = 0x3f; // 用于位与运算以提取位值0x3f--->00111111
    unsigned char utf_one = 0, utf_other = 0x80; // 用于"位或"置标UTF-8编码0x80--->1000000
    wchar_t tmp_wchar =L'0'; // 用于宽字符位置析取和位移(右移位)
    unsigned char tmp_char =L'0';
    if (!src_wchar)//
        return (size_t)-1;
    for (;;) // 检测字节序列长度
    {
        if (src_wchar <= 0x7f){ // <=01111111
            count_bytes = 1; // ASCII字符: 0xxxxxxx( ~ 01111111)
            byte_one = 0x7f; // 用于位与运算, 提取有效位值, 下同
            utf_one = 0x0;
            break;
        }
        if ( (src_wchar > 0x7f) && (src_wchar <= 0x7ff) ){ // <=0111,11111111
            count_bytes = 2; // 110xxxxx 10xxxxxx[1](最多个位, 简写为*1)
            byte_one = 0x1f; // 00011111, 下类推(1位的数量递减)
            utf_one = 0xc0; // 11000000
            break;
        }
        if ( (src_wchar > 0x7ff) && (src_wchar <= 0xffff) ){ //0111,11111111<=11111111,11111111
            count_bytes = 3; // 1110xxxx 10xxxxxx[2](MaxBits: 16*1)
            byte_one = 0xf; // 00001111
            utf_one = 0xe0; // 11100000
            break;cstring转为int
        }
        if ( (src_wchar > 0xffff) && (src_wchar <= 0x1fffff) ){ //UCS-4的支持..
            count_bytes = 4; // 11110xxx 10xxxxxx[3](MaxBits: 21*1)
            byte_one = 0x7; // 00000111
            utf_one = 0xf0; // 11110000
            break;
        }
        if ( (src_wchar > 0x1fffff) && (src_wchar <= 0x3ffffff) ){
            count_bytes = 5; // 111110xx 10xxxxxx[4](MaxBits: 26*1)
            byte_one = 0x3; // 00000011
            utf_one = 0xf8; // 11111000
            break;
        }
        if ( (src_wchar > 0x3ffffff) && (src_wchar <= 0x7fffffff) ){
            count_bytes = 6; // 1111110x 10xxxxxx[5](MaxBits: 31*1)
            byte_one = 0x1; // 00000001
            utf_one = 0xfc; // 11111100
            break;
        }
        return (size_t)-1; // 以上皆不满足则为非法序列
    }
    // 以下几行析取宽字节中的相应位, 并分组为UTF-8编码的各个字节
    tmp_wchar = src_wchar;
    for (int i = count_bytes; i > 1; i--)
    { // 一个宽字符的多字节降序赋值
        tmp_char = (unsigned char)(tmp_wchar & byte_other);///后位与byte_other 00111111
        dest_str[i - 1] = (tmp_char | utf_other);/// 在前面加----跟或
        tmp_wchar >>= 6;//右移位
    }
    //这个时候i=1
    //UTF-8第一个字节位处理,
    //第一个字节的开头"1"的数目就是整个串中字节的数目
    tmp_char = (unsigned char)(tmp_wchar & byte_one);//根据上面附值得来,有效位个数
    dest_str[0] = (tmp_char | utf_one);//根据上面附值得来1的个数
    // 位值析取分组__End!
    return count_bytes;
}
int CDGQDialog::g_f_wcs_to_pchar(CString& wstr,char * p)
{
    wchar_t wc=L'1';
    char c[10]="1";//申请一个缓存
    size_t r=0; //size_t unsigned integer Result of sizeof operator
    int i=0;
    int j=0;
    for(i=0;i<wstr.GetLength();i++)
    {
        wc=wstr.GetAt(i);//得到一个宽字符
        r=g_f_wctou8(c,wc);//将一个宽字符按UTF-8格式转换到p地址
        if(r==-1)//出错判断
            AfxMessageBox(_T("wcs_to_pchar error"));
        p[j]=c[0];//第一个值附给p
        j++;
        if(r>1)
        {
            for(size_t x=1;x<r;x++)
            {
                p[j]=c[x];
                j++;
            }
        }
    }
    //p[j]='0';
    return 1;
}
三.转换实例
void CMytestDlg::OnBnClickedButton2()
{
    // TODO: 在此添加控件通知处理程序代码
    CString ccId=L"2007071";
    CString sql;
    char mySql[100];
    memset(mySql,0,sizeof(mySql));
    sql.Format(L"select cxrq,cxdw,dxrq,dxdw,fxrq,fxdw,cx,flx from j_clxx where trainnum_info_id ='%s'",ccId);
    //wchar_t sql=L'';
    g_f_wcs_to_pchar(sql,mySql);
    CString sql1 =UTF8ToUnicode(mySql);
    MessageBox(sql);
    //g_f_wctou8(mySql,sql);
//      CString str_temp;
//      for (int i=90;i<strlen(mySql);i++)
//      {
//          str_temp.Format(L"%c",mySql[i]);
//          MessageBox(str_temp);
//      }

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。