欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

利用Qt實(shí)現(xiàn)網(wǎng)絡(luò)數(shù)據(jù)報(bào)文大小端數(shù)據(jù)的收發(fā)

 更新時(shí)間:2024年11月28日 11:05:56   作者:灬Sunnnnn  
大小端(Endianness)是計(jì)算機(jī)體系結(jié)構(gòu)的一個(gè)術(shù)語(yǔ),它描述了多字節(jié)數(shù)據(jù)在內(nèi)存中的存儲(chǔ)順序,下面我們來(lái)看看如何利用Qt實(shí)現(xiàn)網(wǎng)絡(luò)數(shù)據(jù)報(bào)文大小端數(shù)據(jù)的收發(fā)吧

1.大小端數(shù)據(jù)簡(jiǎn)介

大小端(Endianness)是計(jì)算機(jī)體系結(jié)構(gòu)的一個(gè)術(shù)語(yǔ),它描述了多字節(jié)數(shù)據(jù)在內(nèi)存中的存儲(chǔ)順序。以下是大小端的定義和它們的特點(diǎn):

大端(Big-Endian)

在大端模式中,一個(gè)字的最高有效字節(jié)(MSB,即最左邊的那位)存儲(chǔ)在最低的內(nèi)存地址處,而最低有效字節(jié)(LSB,即最右邊的那位)存儲(chǔ)在最高的內(nèi)存地址處。

例如,假設(shè)有一個(gè)16位的數(shù)字 0x1234,其在內(nèi)存中的存儲(chǔ)順序如下:

地址增加方向 -->

[ 12 ] [ 34 ]

其中 [12] 是高字節(jié),存儲(chǔ)在低地址處;[34] 是低字節(jié),存儲(chǔ)在高地址處。

小端(Little-Endian)

在小端模式中,情況正好相反:一個(gè)字的最低有效字節(jié)存儲(chǔ)在最低的內(nèi)存地址處,而最高有效字節(jié)存儲(chǔ)在最高的內(nèi)存地址處。

繼續(xù)上面的例子,16位的數(shù)字 0x1234 在小端模式下的存儲(chǔ)順序如下:

地址增加方向 -->

[ 34 ] [ 12 ]

其中 [34] 是低字節(jié),存儲(chǔ)在低地址處;[12] 是高字節(jié),存儲(chǔ)在高地址處。

2.小端數(shù)據(jù)收發(fā)

假設(shè)我們現(xiàn)在有一個(gè)UDP頭的數(shù)據(jù)結(jié)構(gòu)如下所示。

    //UDP協(xié)議頭
    typedef struct
    {
        quint16 type;               //報(bào)文類型
        quint16 num;                //報(bào)文序號(hào),取值范圍為0~65535
        quint32 len;                //報(bào)文長(zhǎng)度
        quint16 srcAddr;            //信源地址
        quint16 dstAddr;            //信宿地址
        quint8  year;               //發(fā)送時(shí)間  年份后兩位   UTC時(shí)間
        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ù)接收:拆包

對(duì)于多字節(jié)的數(shù)據(jù),都需要單獨(dú)使用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實(shí)現(xiàn)網(wǎng)絡(luò)數(shù)據(jù)報(bào)文大小端數(shù)據(jù)的收發(fā)的文章就介紹到這了,更多相關(guān)Qt大小端數(shù)據(jù)收發(fā)內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

最新評(píng)論