浅析QStringr的Unicode存储特性(一)

在看Qt相关的文档时,不断看到Qt对于i18n和Unicode的支持如何,一直没有个直观和底层的认识,最近写了些简单的例子,感觉结合实例能更好理解Qt内部对于字符串存储的转换机制。

下面的例子都以"中文"这个简单的字符串作为示例。

编译和调试工具:GCC &GDB
本地locale:zh_CN.UTF-8

字符 '中',Unicode码值U+4E2D, 对应的UTF-8编码形式为   E4 B8 AD (大端)
字符 “文”, Unicode码值U+6587,  对应的UTF-8编码形式为   E6 A6 87  (大端)

例子1 .不使用Qt,直接用char数组存储字符串

char  buffer[] = " 中文 " ;
cout
<< buffer << endl;


输出结果:

 

使用gdb查看buffer中存储的值

(gdb) x  / 8xb  & buffer
0xbfa20879 :      0xe4    0xb8    0xad    0xe6    0x96    0x87    0x00      0x20

可以很清楚的观察到此时buffer中存储的就是“中文”对应的UTF-8编码,由于此时输出的字符串和locale采用的是相同的编码格式,因此不会出现乱码形式。

示例2 使用QString存储字符串,并利用QChar看清楚“中文”这个字符串在QString中究竟是如何存储的。

    QString chinese="中文";
    QChar * pch=chinese.data();


上面的QString::data()的作用是返回一个指向所存储数据的QChar *指针,正如Qt的文档中所描述的一样,QString可以看作是QVector<QChar>

下面使用gdb查看pch所指向的区域存储的内容

(gdb) x  / 16xb pch
0x804b192 :       0xe4    0x00    0xb8    0x00    0xad    0x00    0xe6    0x00
0x804b19a :       0x96    0x00    0x87    0x00    0x00    0x00      0x00      0x00

仔细观察,请注意QChar中存放的是16 bit 的Unicode的值;答案很明显,pch指向的区域存放的值依次是 U+00e4,U+00b8,U+00ad,U+00e6,U+0096,U+0087,U+0000这七个Unicode码值。

是不是觉得这个序列看着有些眼熟?对了,这和第一个例子中gdb中查看到的值很相像,确切的说是值相同,不同的是示例1中的每个字节在在示例2中都用2字节来表示——这就是Qt所谓的QString的内部存储使用Unicode的底层含义!

这里,把上面的脉络稍微梳理一下:

首先,我们从示例1中已经知道,源代码中的“中文"在我的实验环境下(locale为zh_CN.UTF-8)被编码为8 bit 的 Ascii 字符串“ 0xe4    0xb8    0xad    0xe6    0x96    0x87    0x00”;

其次,在示例2中定义QString 类型的变量chinese时用"中文"为其初始化,因为QString内部存储采用Unicode,所以每个字符用16 bit来表示,因此0xe4 扩展为 0x00e4, 0xb8扩展为0x00b8,依次类推。

因此,“中文”在QString内部的存储形式就是

0xe4    0x00    0xb8    0x00    0xad    0x00    0xe6    0x00
0x96    0x00    0x87    0x00    0x00    0x00

如何,看了这个简单的例子,是否对Qt的Unicode支持还感觉很模糊呢?
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值