Qt实现对于一个大的字节流包找到自己需要的小的包

62 篇文章 14 订阅
50 篇文章 0 订阅

对于二进制字节流,我以往的方法都是采用指针的形式,比如一个头指针,一个尾指针,两者定位,得到需要的包头与包尾。

这个方法比较原始,今天发现在Qt中,有着更好的解决方案:
就是利用QByteArray本身自带的indexOf()函数来进行判断。
例如,想寻找一个包头为0X0000BBAA,包尾为0XFFEE0000的数据包,可以采用下面的方式:

//char chHead[4] = {0XAA, 0XBB, 0X00, 0X00};
//char chTail[4] = {0X00, 0X00, 0XEE, 0XFF};
//上面的代码之所以注释掉,是因为会触发一个“截断警告”,建议采用下面的方式
char chHead[4] = {(char)0XAA, (char)0XBB, (char)0X00, (char)0X00};
char chTail[4] = {(char)0X00, (char)0X00, (char)0XEE, (char)0XFF};

QByteArray arrHead, arrTail;
/*! 下面的作用是,将包头和包尾分别整合起来,用于判断 */
arrHead.append(chHead, 4);
arrTail.append(chTail, 4);

/*! 找到头尾的索引值(假设数据包为arrData) */
int iHeadIndex = arrData.indexOf(arrData);//这种写法实际上不严谨,因为如果没找到的话,indexOf函数将返回-1
int iTailIndex = arrData.indexOf(arrData);//同上,一样不严谨

//假设上面的索引值都是正确的(这里因为仅仅是演示,就不写判断了),取得我想要的包
QByteArray arrResult = arrData.mid(iHeadIndex, iTailIndex - iHeadIndex + 4);//这里面+4的原因是包尾所占的大小为4

这样就能取得我们想要类型的数据包了。

如果这个数据里面有很多个我们需要的包的话,就需要采用循环的方式了,例子代码如下(同样假设数据包为arrData):

char chHead[2] = {(char)0XAA, (char)0XBB);
char chTail[4] = {(char)0X00, (char)0X00, (char)0XEE, (char)0XFF};

QByteArray arrHead, arrTail;
arrHead.append(chHead, 2);
arrTail.append(chTail, 4);

int iFrom = 0;//设置搜索起点(每次找完之后,都需要更新这个搜索起点)
/*! 判断条件为能搜索到(如果搜索不到,返回值为-1,详见Qt帮助文档) */
while (arrData.indexOf(arrHead, iFrom) != -1)
{
	int iHeadIndex = arrData.indexOf(arrHead, iFrom);
	int iTailIndex = arrData.indexOf(arrTail, iHeadIndex);//对于包尾的搜索起点设置为刚刚搜索到的头就可以了,简化搜索范围
	
	QByteArray arrResult = arrData.mid(iHeadIndex, iTailIndex - iHeadIndex + arrTail.size());//这里就不写具体的数字了,这样更好
	
	//对得到的数据进行处理
	DoSthWithArrResult(arrResult);

	iFrom = iHeadIndex + 1;//这里面的位置只要是在上次的头的后面就行,具体的偏移量自己考虑,这里采用的偏移量的大小是1,可以根据需要自己设定。
}

上面的这一段代码,就是对于具有多个需要类型的包的整包的解析。

总结:
对于Qt,多多采用Qt本身已经封装好的函数,这样不仅快捷,而且更加安全。
当然,我不是反对自己写函数,主要是现在的技术比较差,自己写的话可能会有一些边界问题处理不好,因此我建议多多使用已经封装好的函数,对于这些函数的实现原理,可以自己去看看源码,学习即可。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值