目的:实现将字符串装配成一个完整的协议对象。 main函数测试目标 将完整的协议字符串分两次写到内存中,通过 TxtMsgAssembler类完成对协议的装配 代码: txtmsgassembler.h
#ifndef TXTMSGASSEMBLER_H #define TXTMSGASSEMBLER_H #include <QObject> #include <QQueue> #include <QSharedPointer> #include "TextMessage.h" class TxtMsgAssembler : public QObject { Q_OBJECT QQueue<char> m_queue;//存储字节流 QString m_type; int m_length; QString m_data; public: explicit TxtMsgAssembler(QObject *parent = nullptr); QSharedPointer<TextMessage> assemble();//从内部容器中获取字节数据,尝试装配字节对象 QSharedPointer<TextMessage> assemble(const char* data,int length); void prepare(const char* data, int len);//将数据转存到内部容器,用于后续协议对象装配 void reset(); void clear(); bool makeTypeAndLength(); TextMessage* makeMessage(); QString fetch(int n); signals: public slots: }; #endif // TXTMSGASSEMBLER_Htxtmsgassembler.cpp
#include "txtmsgassembler.h" TxtMsgAssembler::TxtMsgAssembler(QObject *parent) : QObject(parent) { } QSharedPointer<TextMessage> TxtMsgAssembler::assemble(const char *data, int length) { prepare(data,length); return assemble(); } QSharedPointer<TextMessage> TxtMsgAssembler::assemble() { TextMessage* ret=NULL; bool tryMakeMsg=false; if(m_type=="") { tryMakeMsg=makeTypeAndLength(); } else { tryMakeMsg=true; } if(tryMakeMsg) { ret = makeMessage(); } if(ret!=NULL) { clear(); } return QSharedPointer<TextMessage>(ret); } void TxtMsgAssembler::prepare(const char* data, int len) { if(data!=NULL) { for(int i=0;i<len;i++) { m_queue.enqueue(data[i]); } } } void TxtMsgAssembler::reset() { clear(); m_queue.clear(); } void TxtMsgAssembler::clear() { m_type=""; m_length=0; m_data=""; } bool TxtMsgAssembler::makeTypeAndLength() { bool ret=(m_queue.length()>=8); if(ret) { m_type=fetch(4); QString len =fetch(4).trimmed(); m_length=len.toInt(&ret,16); if(!ret) { clear(); } } return ret; } TextMessage* TxtMsgAssembler::makeMessage() { TextMessage* ret=NULL; if(m_type!="") { int needlen=m_length-m_data.length(); int n=(needlen<=m_queue.length())?needlen:m_queue.length(); m_data+=fetch(n); if(m_length==m_data.length()) { ret=new TextMessage(m_type,m_data); } } return ret; } QString TxtMsgAssembler::fetch(int n) { QString ret; for(int i=0;i<n;++i) { ret+=m_queue.dequeue(); } return ret; }main.cpp
#include <QCoreApplication> #include <QDebug> #include "textmessage.h" #include "txtmsgassembler.h" int main(int argc, char *argv[]) { QCoreApplication a(argc, argv); TextMessage tm("AB","1234567890"); QString message=tm.serialize(); qDebug()<<message; QString s1=message.mid(0,5); QString s2=message.mid(5); QSharedPointer<TextMessage> tmt; TxtMsgAssembler as; tmt=as.assemble(s1.toStdString().c_str(),s1.length()); if(tmt!=NULL) { qDebug()<<"assembel sucessed."; qDebug()<<tmt->type(); qDebug()<<tmt->length(); qDebug()<<tmt->data(); } tmt=as.assemble(s2.toStdString().c_str(),s2.length()); if(tmt!=NULL) { qDebug()<<"assembel sucessed."; qDebug()<<tmt->type(); qDebug()<<tmt->length(); qDebug()<<tmt->data(); } return a.exec(); }说明:textmessage.h参考上一节同名文件
效果: