QT 字符串转换的一个BUG

代码: 

QString str = "abc"; // 第 1 行

QByteArray arr = str.toLocal8Bit(); // 第 2
LPCSTR pStr = arr.data(); // 第 3
qDebug() << "第1个字串: " << pStr; // 第 4
LPCSTR pStr1 = str.toLocal8Bit().data(); // 第 5

qDebug() << "第2个字串: " << pStr1; // 第 6


结果: 

第1个字串:  abc 
第2个字串:   


原因: 

QString::toLocal8Bit 返回一个QByteArray对象, QByteArray::data 返回该对象的数据指针, 所以第 4 行输出了arr对象的数据指针. 

但是在第5行代码里生成的QByteArray对象是隐含的, 在执行到第 6 行代码时该对象已经被释放掉了, 所以 pStr1 指向的该对象数据指针已不可用, 导致第 6 行的输出结果不正确.


看汇编代码会一目了然: 


QString str = "abc";
00262668  push        26CE84h  
0026266D  lea         ecx,[ebp-1Ch]  
00262670  call        dword ptr [__imp_QString::QString (271958h)]  
00262676  mov         dword ptr [ebp-4],0  


QByteArray arr = str.toLocal8Bit();
0026267D  lea         eax,[ebp-10h]  
00262680  push        eax  
00262681  lea         ecx,[ebp-1Ch]  
00262684  call        dword ptr [__imp_QString::toLocal8Bit (2719A0h)]  
0026268A  mov         byte ptr [ebp-4],1  


LPCSTR pStr = arr.data();
0026268E  lea         ecx,[ebp-10h]  
00262691  call        dword ptr [__imp_QByteArray::data (271A04h)]  
00262697  mov         dword ptr [ebp-14h],eax  


qDebug() << "第1个字串: " << pStr;
0026269A  mov         ecx,dword ptr [ebp-14h]  
0026269D  push        ecx  
0026269E  push        26CE88h  
002626A3  lea         edx,[ebp-20h]  
002626A6  push        edx  
002626A7  call        dword ptr [__imp_qDebug (271A08h)]  
002626AD  add         esp,4  
002626B0  mov         dword ptr [ebp-30h],eax  
002626B3  mov         eax,dword ptr [ebp-30h]  
002626B6  mov         dword ptr [ebp-34h],eax  
002626B9  mov         byte ptr [ebp-4],2  
002626BD  mov         ecx,dword ptr [ebp-34h]  
002626C0  call        dword ptr [__imp_QDebug::operator<< (271A10h)]  
002626C6  mov         ecx,eax  
002626C8  call        dword ptr [__imp_QDebug::operator<< (271A10h)]  
002626CE  mov         byte ptr [ebp-4],1  
002626D2  lea         ecx,[ebp-20h]  
002626D5  call        dword ptr [__imp_QDebug::~QDebug (271924h)]  


LPCSTR pStr1 = str.toLocal8Bit().data();
002626DB  lea         ecx,[ebp-24h]  
002626DE  push        ecx  
002626DF  lea         ecx,[ebp-1Ch]  
002626E2  call        dword ptr [__imp_QString::toLocal8Bit (2719A0h)]  
002626E8  mov         dword ptr [ebp-38h],eax  
002626EB  mov         edx,dword ptr [ebp-38h]  
002626EE  mov         dword ptr [ebp-3Ch],edx  
002626F1  mov         byte ptr [ebp-4],3  
002626F5  mov         ecx,dword ptr [ebp-3Ch]  
002626F8  call        dword ptr [__imp_QByteArray::data (271A04h)]  
002626FE  mov         dword ptr [ebp-18h],eax  
00262701  mov         byte ptr [ebp-4],1  
00262705  lea         ecx,[ebp-24h]  
00262708  call        dword ptr [__imp_QByteArray::~QByteArray (271928h)]   // 释放隐含的QByteArray对象


qDebug() << "第2个字串: " << pStr1;
0026270E  mov         eax,dword ptr [ebp-18h]  
00262711  push        eax  
00262712  push        26CE94h  
00262717  lea         ecx,[ebp-28h]  
0026271A  push        ecx  
0026271B  call        dword ptr [__imp_qDebug (271A08h)]  
00262721  add         esp,4  
00262724  mov         dword ptr [ebp-40h],eax  
00262727  mov         edx,dword ptr [ebp-40h]  
0026272A  mov         dword ptr [ebp-44h],edx  
0026272D  mov         byte ptr [ebp-4],4  
00262731  mov         ecx,dword ptr [ebp-44h]  
00262734  call        dword ptr [__imp_QDebug::operator<< (271A10h)]  
0026273A  mov         ecx,eax  
0026273C  call        dword ptr [__imp_QDebug::operator<< (271A10h)]  
00262742  mov         byte ptr [ebp-4],1  
00262746  lea         ecx,[ebp-28h]  
00262749  call        dword ptr [__imp_QDebug::~QDebug (271924h)]  
}


0026274F  mov         byte ptr [ebp-4],0  
00262753  lea         ecx,[ebp-10h]  
00262756  call        dword ptr [__imp_QByteArray::~QByteArray (271928h)]   // 释放 arr 对象
0026275C  mov         dword ptr [ebp-4],0FFFFFFFFh  
00262763  lea         ecx,[ebp-1Ch]  
00262766  call        dword ptr [__imp_QString::~QString (271960h)]  
0026276C  mov         ecx,dword ptr [ebp-0Ch]  
0026276F  mov         dword ptr fs:[0],ecx  
00262776  pop         ecx  
00262777  mov         esp,ebp  
00262779  pop         ebp  
0026277A  ret         4  

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值