利用Qt實現(xiàn)網(wǎng)絡(luò)數(shù)據(jù)報文大小端數(shù)據(jù)的收發(fā)
1.大小端數(shù)據(jù)簡介
大小端(Endianness)是計算機體系結(jié)構(gòu)的一個術(shù)語,它描述了多字節(jié)數(shù)據(jù)在內(nèi)存中的存儲順序。以下是大小端的定義和它們的特點:
大端(Big-Endian)
在大端模式中,一個字的最高有效字節(jié)(MSB,即最左邊的那位)存儲在最低的內(nèi)存地址處,而最低有效字節(jié)(LSB,即最右邊的那位)存儲在最高的內(nèi)存地址處。
例如,假設(shè)有一個16位的數(shù)字 0x1234,其在內(nèi)存中的存儲順序如下:
地址增加方向 -->
[ 12 ] [ 34 ]
其中 [12] 是高字節(jié),存儲在低地址處;[34] 是低字節(jié),存儲在高地址處。
小端(Little-Endian)
在小端模式中,情況正好相反:一個字的最低有效字節(jié)存儲在最低的內(nèi)存地址處,而最高有效字節(jié)存儲在最高的內(nèi)存地址處。
繼續(xù)上面的例子,16位的數(shù)字 0x1234 在小端模式下的存儲順序如下:
地址增加方向 -->
[ 34 ] [ 12 ]
其中 [34] 是低字節(jié),存儲在低地址處;[12] 是高字節(jié),存儲在高地址處。
2.小端數(shù)據(jù)收發(fā)
假設(shè)我們現(xiàn)在有一個UDP頭的數(shù)據(jù)結(jié)構(gòu)如下所示。
//UDP協(xié)議頭 typedef struct { quint16 type; //報文類型 quint16 num; //報文序號,取值范圍為0~65535 quint32 len; //報文長度 quint16 srcAddr; //信源地址 quint16 dstAddr; //信宿地址 quint8 year; //發(fā)送時間 年份后兩位 UTC時間 quint8 month; quint8 day; quint8 hour; quint8 minute; quint8 second; }UdpHeader;
數(shù)據(jù)發(fā)送:組包。
QByteArray pack(const Protocol::UdpHeader &header) { QByteArray byte; byte.append((char*)&(header.type),2); byte.append((char*)&(header.num),2); byte.append((char*)&(header.len),4); byte.append((char*)&(header.srcAddr),2); byte.append((char*)&(header.dstAddr),2); QString format = "yy-MM-dd-hh-mm-ss"; QDateTime dateTime = QDateTime::currentDateTime(); dateTime.setTimeSpec(Qt::LocalTime); QDateTime utcTime = dateTime.toUTC(); QString strUtcTime = utcTime.toString(format); QStringList timeList = strUtcTime.split('-'); quint8 year = timeList.at(0).toInt(); quint8 month = timeList.at(1).toInt(); quint8 day = timeList.at(2).toInt(); quint8 hour = timeList.at(3).toInt(); quint8 minute = timeList.at(4).toInt(); quint8 sec = timeList.at(5).toInt(); byte.append(year); byte.append(month); byte.append(day); byte.append(hour); byte.append(minute); byte.append(sec); return byte; }
數(shù)據(jù)接收:拆包
void unPack(const QByteArray &byte, Protocol::UdpHeader &header) { if(byte.size() != UDP_HEADER_LEN) { return; } memcpy(&header,byte.data(),sizeof(Protocol::UdpHeader)); }
3.大端數(shù)據(jù)收發(fā)
還是上面的頭例子。
數(shù)據(jù)發(fā)送:組包
使用QDataStream類作為輔助,設(shè)置setByteOrder為大端序列。
QByteArray packBigEndian(const Protocol::UdpHeader &header) { QByteArray byte; QDataStream stream(&byte,QIODevice::WriteOnly); stream.setByteOrder(QDataStream::BigEndian); stream<<(header.type); stream<<(header.num); stream<<(header.len); stream<<(header.srcAddr); stream<<(header.dstAddr); QString format = "yy-MM-dd-hh-mm-ss"; QDateTime dateTime = QDateTime::currentDateTime(); dateTime.setTimeSpec(Qt::LocalTime); QDateTime utcTime = dateTime.toUTC(); QString strUtcTime = utcTime.toString(format); QStringList timeList = strUtcTime.split('-'); quint8 year = timeList.at(0).toInt(); quint8 month = timeList.at(1).toInt(); quint8 day = timeList.at(2).toInt(); quint8 hour = timeList.at(3).toInt(); quint8 minute = timeList.at(4).toInt(); quint8 sec = timeList.at(5).toInt(); stream<<year; stream<<month; stream<<day; stream<<hour; stream<<minute; stream<<sec; return byte; }
數(shù)據(jù)接收:拆包
對于多字節(jié)的數(shù)據(jù),都需要單獨使用qToBigEndian轉(zhuǎn)換為大端。
void unPackBigEndian(const QByteArray &byte, Protocol::UdpHeader &header) { if(byte.size() != UDP_HEADER_LEN) { return; } memcpy(&header,byte.data(),sizeof(Protocol::UdpHeader)); header.type = qToBigEndian(header.type); header.num= qToBigEndian(header.num); header.len= qToBigEndian(header.len); header.srcAddr= qToBigEndian(header.srcAddr); header.dstAddr= qToBigEndian(header.dstAddr); }
到此這篇關(guān)于利用Qt實現(xiàn)網(wǎng)絡(luò)數(shù)據(jù)報文大小端數(shù)據(jù)的收發(fā)的文章就介紹到這了,更多相關(guān)Qt大小端數(shù)據(jù)收發(fā)內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Qt重寫QComboBox實現(xiàn)下拉展示多列數(shù)據(jù)
這篇文章主要為大家詳細介紹了Qt如何重寫QComboBox實現(xiàn)下拉展示多列數(shù)據(jù),文中的示例代碼講解詳細,感興趣的小伙伴可以跟隨小編一起學(xué)習(xí)一下2024-11-11OpenGL實現(xiàn)不規(guī)則區(qū)域填充算法
這篇文章主要為大家詳細介紹了OpenGL實現(xiàn)不規(guī)則區(qū)域填充算法,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下2020-02-02C++設(shè)計模式編程中Facade外觀模式的使用實例解析
這篇文章主要介紹了C++設(shè)計模式編程中Facade外觀模式的使用實例解析,外觀模式的主要用途就是為子系統(tǒng)的復(fù)雜處理過程提供方便的調(diào)用方法,需要的朋友可以參考下2016-03-03