Important: Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

[solved] Convert a char array into qint16 array with qFromBigEndian



  • In my program I receive an array of const char *data, It's BigEndian type so I would like to use the function qFromBigEndian<qint16> to convert the array into a QVector of qint16. But it crashed. I assume that I can't just convert it directly from the char array into a QVector, what is the correct way of converting the char array into a qint16 array? Here is the code snippet:

    void TestFunction::receiveData(const char *data, int channelCount)
    {
        // channelCount is the number of qint16 the data contains
        QVector<qint16> destination;
    
        // the following line crashes: what is the correct data type for destination?
        qFromBigEndian<qint16>(ptr, channelCount, &destination)
    }
    

    Thanks!



  • You need to first allocate the memory by making the vector non-empty and having the same byte size as you want to read from the const char *data, and then pass the allocated memory address, not the vector variable's address, to the function.

    QVector<qint16> destination(channelCount);
    qFromBigEndian<qint16>(data, channelCount, destination.data());
    

    And you need to be sure that channelCount = bytesizeofdata / 2.



  • @Bonnie said in Convert a char array into qint16 array with qFromBigEndian:

    And you need to be sure that channelCount = bytesizeofdata / 2.

    Hi @Bonnie, thanks a lot for your help! I still can't get the second argument right. In my case, the data array is of length 4096 byte, but I only want to copy the first 64 numbers out of the array as qint16 into my QVector (meaning the destination array would be pre-allocated with size 64). Is that possible with this function at all? Or I need to copy the whole data source into the destination?


  • Lifetime Qt Champion

    @Thinium
    Hi
    Maybe i misunderstood something but cant you just do
    qFromBigEndian<qint16>(data, 64, destination.data());

    if you dont want all of channelCount ?



  • @Thinium
    Just as @mrjj said, if you only need 64 numbers, then

    int count = qMin(64, channelCount);  //just in case of channelCount is not big enough
    QVector<qint16> destination(count);
    qFromBigEndian<qint16>(data, count, destination.data());
    


  • Thanks to @mrjj and @Bonnie ! it works. My problem actually was that the data source is 32 bit but not 16 bit. So I need to use qint32 instead. All good now :)



  • @mrjj for some reason I need to use std::vector<qint32> instead of QVector<qint32> as the destination, but I notice that if I use:

    std::vector<qint32> destination;
    destination.reserve(channelCount);
    qFromBigEndian<qint32>(data, 64, destination.data());
    

    The destination doesn't get filled with anything . Does that mean the destination could only be a QVector?


  • Lifetime Qt Champion

    Hi
    Well its
    template <typename T> void qFromBigEndian(const void *src, qsizetype count, void *dest)

    so std::vector should also work as far as i can see.



  • @Thinium
    Of course std::vector is also usable.
    The problem is reserve() only allocate the memory, but the size() is still 0.
    The qFromBigEndian function only fills the memory, it won't increase the vector size.
    Also with an empty vector, the result of data() may be invalid.
    So, either use

    std::vector<qint32> destination(channelCount);
    

    or

    std::vector<qint32> destination;
    destination.resize(channelCount);
    

Log in to reply