我的问题是这样的:我有一个名为'Register'的课程。它有一个名为'trainName'的字符串属性及其setter:
class Register {
private:
string trainName;
public:
string getTrainName();
};
事实上,它更长,但我想让这更简单。
在其他类中,我将几个Register对象复制到二进制文件中,之前设置了trainName。
Register auxRegister = Register();
auxRegister.setName("name");
for(int i = 0; i < 10; i++) {
file.write(reinterpret_cast<char*>(&auxRegister),sizeof(Register));
}
稍后,我尝试从二进制文件中检索寄存器:
Register auxRegister = Register();
while(!file.eof()) { //I kwnow this is not right. Which is the right way?
file.read(reinterpret_cast<char*>(&auxRegister), sizeof(Register));
}
它发生它不起作用。事实上,Register确实有更多属性(它们是int),我可以检索它们,但字符串不是这样。
我做错了吗?在处理二进制文件和字符串时,我应该考虑一些因素吗?
非常感谢。
答案 0 :(得分:2)
你不能以这种方式编写字符串,因为它几乎肯定包含指向某些结构的指针和其他无法完成序列化的二进制内容。 您需要编写自己的序列化函数,并编写字符串长度+字节(例如)或使用完整的库,例如,protobuf,它可以为您解决序列化问题。
编辑:请参阅praetorian的回答。比我的好得多(即使在编辑时得分较低)。
答案 1 :(得分:2)
std::string
类包含指向存储字符串的缓冲区的指针(以及其他成员变量)。字符串缓冲区本身不是类的一部分。因此,写出类实例的内容是行不通的,因为如果你这样做的话,字符串永远不会成为你转储到文件中的一部分。你需要得到一个指向字符串的指针并写下来。
Register auxRegister = Register();
auxRegister.setName("name");
auto length = auxRegister.size();
for(int i = 0; i < 10; i++) {
file.write( auxRegister.c_str(), length );
// You'll need to multiply length by sizeof(CharType) if you
// use a wstring instead of string
}
稍后,要读取字符串,您必须跟踪写入文件的字节数;或者可能从文件本身获取该信息,具体取决于文件格式。
std::unique_ptr<char[]> buffer( new char[length + 1] );
file.read( buffer, length );
buffer[length] = '\0'; // NULL terminate the string
Register auxRegister = Register();
auxRegister.setName( buffer );