1
votes

I want to read multiple float values from the file in which I already wrote using this:

QDataStream &operator<<(QDataStream &out, const SomeClass &obj)
{
    out << obj.maxX << obj.maxY << obj.minX << obj.minY;

    out << (int) obj.points.size();

    for(int c = 0; c < obj.points.size(); ++c){
        out << obj.points.at(c).floatX << obj.points.at(c).floatY;
    }

    return out;
}

And I can read this file using this:

QDataStream &operator>>(QDataStream &in, SomeClass &obj)
{
    in >> obj.maxX >> obj.maxY >> obj.minX >> obj.minY;

    int pointsSize = 0;
    in >> pointsSize;

    for(int c = 0; c < pointsSize; ++c){

        float x = 0, y = 0;

        in >> x >> y;

        obj.points.push_back(Point(x, y));
    }
    return in;
}

But it's not so efficient to read these floats separately, so I want to read first 4 floats(maxX, maxY, minX, minY) together, then read one int, and then read all other floats(instances of floatX and floatY) together.
I already tried this:

 QDataStream in(&file);
 QByteArray ba;
 in.readRawData(ba.data(), 4*sizeof(float));

 float array[4];
 memcpy(&array, ba.constData(), ba.size());

But it gives wrong result.

So, how can I read many floats in one buffer array or vector?

UPD:

I already saw getline() too, but how exactly can I iterate over char * from binary file and get floats from it?

1
Is your memcopy backwards with source and destination swapped? [This does not look correct --- memcpy(&array, ba.constData(), ba.size());]William J Bagshaw
Are you sure reading them separately is inefficient? Did you profile it? The way you want to do this adds an additional copy, so I wouldn't be as sure that this is faster.Karsten Koop
@WilliamJBagshaw I know that this isn't correct, but I don't know how to fix it in the right waykonstantin_doncov
Your approach assumes that the data layout (like endianess) in the file and in memory is the same. By using the QDataStream operators, you can be sure that this gets taken care of. So I wouldn't do the reading of raw bytes if it can be avoided, and prefer the official functions.Karsten Koop
So I guess the function is not just called once, but millions of times? I don't think that disk i/o makes a difference, as data from disk is cached and buffered in several layers, almost never only 4 bytes will be read from disk.Karsten Koop

1 Answers

1
votes

From docs:

"The QDataStream class provides serialization of binary data to a QIODevice."

If you use getRawData() method, binary data is what you get. Thats the reason why are you geting wrong results when interpreting them as something else.

If you want to speed things up, my advice would be to dont use QDataStream, and use regular standard fstream instead.

To avoid multiple readings, read whole line using getline() and then iterate over numbers stored in there.