converting c++ class to a byte array

2019-08-22 11:39发布

问题:

It is possible to convert the following Student class to a binary file by writing it with ios::binary

#include <fstream>
#include <iostream>
using namespace std;

class Student{
    public:
        char name[40], address[120], gender;
        double age;
        bool is_blabla;
};

int main() {

    Student one;
    strcpy(one.name, "Cancan Can");
    strcpy(one.address, "example example exampla");
    one.gender = 'M';
    one.age = 25;
    one.is_blabla = true;

    ofstream ofs("fifthgrade.ros", ios::binary);
    ofs.write((char *)&one, sizeof(one));

    Student two;
    ifstream ifs("fifthgrade.ros", ios::binary);
    ifs.read((char *)&two, sizeof(two));

    // check if the data is OK
    cout << "Student Name: " << two.name << endl;


    return 0;
}

The file looks like as follows:

http://i.imgur.com/GfkheWs.png

So how can I do the same thing to convert the class to a byte (or say char*) array in this case?

Edit: But in this case, Let's say I have a class having methods. The answers you gave is telling me to write my own bitwise operators to serialize a complex class. Can you refer to a good source teaching how it can be done or a small sample/example for it?

Edit2: I have to avoid using extra libraries because I may deserialize the serialized code on a machine/compiler that I cannot import most of the libraries (for example I will try to deserialize the code on an nvcc compiled code).

Example dummy class would be like this:

class Student{
    public:
        char name[40], address[120], gender;
        double age;
        bool is_blabla;

        void set_values (int,int);
        int doubleage() {return age*2;}
};

回答1:

Just use a std::stringstream rather than std::ofstream.

Then, access the char* using std::stringstream::str() (This return's a std::string, on which you can retrieve a char* using std::string::c_str()).



回答2:

All objects can be accessed as their constituent chars, just get a pointer and cast it.

Still, even if you want to write it to a binary file (in contrast to writing a textual representation), do not just write its raw bytes:

  • The object might contain a number of non-value-bits (Like padding, unused buffers, whatever). Those might contain previously recorded information, which you should not leak.
  • The object might contain pointers, handles or other references to additional data. Those cannot be recovered from a bitwise-copy, as the information they indicate is the important part and won't be there.

BTW: ios::binary just disables translation of text-files. (Identity on Unixoids, newline-conversion on windows...)



回答3:

If you need a more enhanced way, consider the following ways:

  1. Boost.Serialization (http://www.boost.org/doc/libs/1_56_0/libs/serialization/doc/index.html)
  2. Google Protocol Buffers (https://developers.google.com/protocol-buffers/)