MattSt
MattSt

Reputation: 1192

Writing/Reading strings in binary file-C++

I searched for a similar post but couldn't find something that could help me.

I' m trying to first write the integer containing the string length of a String and then write the string in the binary file.

However when i read data from the binary file i read integers with value=0 and my strings contain junk.

for example when i type 'asdfgh' for username and 'qwerty100' for password i get 0,0 for both string lengths and then i read junk from the file.

This is how i write data to the file.

std::fstream file;

file.open("filename",std::ios::out | std::ios::binary | std::ios::trunc );

Account x;

x.createAccount();

int usernameLength= x.getusername().size()+1; //+1 for null terminator
int passwordLength=x.getpassword().size()+1;

file.write(reinterpret_cast<const char *>(&usernameLength),sizeof(int));
file.write(x.getusername().c_str(),usernameLength);
file.write(reinterpret_cast<const char *>(&passwordLength),sizeof(int));
file.write(x.getpassword().c_str(),passwordLength);

file.close();

Right below in the same function i read the data

file.open("filename",std::ios::binary | std::ios::in );

char username[51];
char password[51];

char intBuffer[4];

file.read(intBuffer,sizeof(int));
file.read(username,atoi(intBuffer));
std::cout << atoi(intBuffer) << std::endl;
file.read(intBuffer,sizeof(int));
std::cout << atoi(intBuffer) << std::endl;
file.read(password,atoi(intBuffer));

std::cout << username << std::endl;
std::cout << password << std::endl;

file.close();

Upvotes: 1

Views: 1488

Answers (2)

Błażej Czapp
Błażej Czapp

Reputation: 2633

When reading the data back in you should do something like the following:

int result;
file.read(reinterpret_cast<char*>(&result), sizeof(int));

This will read the bytes straight into the memory of result with no implicit conversion to int. This will restore the exact binary pattern written to the file in the first place and thus your original int value.

Upvotes: 1

Kathir
Kathir

Reputation: 11

file.write(reinterpret_cast<const char *>(&usernameLength),sizeof(int));

This writes sizeof(int) bytes from the &usernameLength; which is binary representation of integer and depends on the computer architecture (little endian vs big endian).

atoi(intBuffer))

This converts ascii to integer and expect the input to contain character representation. e.g. intBuffer = { '1', '2' } - would return 12.

You can try to read it in the same way you have written -

*(reinterpret_cast<int *>(&intBuffer))

But it can potentially lead to unaligned memory access issues. Better use serialization formats like JSON, which would be helpful to read it in cross-platform ways.

Upvotes: 0

Related Questions