Запись и чтение объекта из бинарного файла

113
11 декабря 2020, 06:50
#include <iostream>
#include <vector>
#include <fstream>
#include <string>   
using namespace std;
/* run this program using the console pauser or add your own getch, system("pause") or input loop */
class foo
{
public:
    string Name = "Баби";
    int Age = 5;
    void show()
    {
        cout << "Name = " << Name << endl;
        cout << "Age = " << Age << endl;
    }
    void write(ostream& os) const
    {
        os.write((const char*)& Age, sizeof Age);
        size_t len = Name.length();
        os.write((const char*)& len, sizeof len);
        os.write(Name.c_str(), len);
    }
    void read(istream& in)
    {
        in.read((char*)& Age, sizeof Age);
        size_t len;
        in.read((char*)& len, sizeof len);
        Name.resize(len);
        in.read(&Name[0], len);
    }
};

int main(int argc, char** argv) {
    setlocale(LC_ALL, "Rus");
    foo* obj = new foo();
    obj->Age = 5;
    obj->Name = "Масло";
    ofstream file("file.bin", ios::binary | ios::app);
    if (file.is_open()) {
        obj->write(file);
        obj->show();
    }
    file.close();
    foo* result = new foo();
    ifstream file1("file.bin", ios::binary);
    if (file1.is_open()) {
        result->read(file1);
        file1.close();
        result->show();
    }
    file1.close();
    return 0;
}

Неправильно записывает и читает из файла. Записывает age = 5и Name = "Масло", а выводит age=0 и Name = "". В чем может быть проблема?

Answer 1

Файл не забывайте закрывать. Перед тем как пытаться открывать файл на чтение, надо не забывать закрыть предыдущее открытие (на запись). И не забывайте проверять, успешно ли вы у вас открылся файл - тогда бы вы сами поняли, почему "не работает" чтение.

Запись/чтение у вас сделано не так эффективно как могло бы, но тем не менее все правильно.

Более эффективно:

  1. Если вы записываете длину строки, то записывать вместе со строкой ее нулевой символ не обязательно.

  2. При чтении строки ее можно аккуратно прочитать прямо внутрь std::string, без создания промежуточного буфера

Например

void write(ostream& os) const
{
  os.write((const char*) &Age, sizeof Age);
  size_t len = Name.length();
  os.write((const char*) &len, sizeof len);
  os.write(Name.c_str(), len);
}
void read(istream& in)
{
  in.read((char*) &Age, sizeof Age);
  size_t len;                       
  in.read((char*) &len, sizeof len);
  Name.resize(len);
  in.read(Name.data(), len); // или `in.read(&Name[0], len);`
}
READ ALSO
Иероглифы вместо русского текста в коде

Иероглифы вместо русского текста в коде

Переустановил Windows, поставив английскую версию (United States)После этого все файлы кода в Visual Studio, которые были написаны на русской версии, искажены,...

88
Qt5: как понять на каком из lineEdit стоит фокус

Qt5: как понять на каком из lineEdit стоит фокус

На форме есть 2 lineEdit'aЕсть на форме куча кнопок а-ля цифровая клавиатура (делаю десктоп-приложение с адаптацией под тачскрины)

122
формане отправляет input

формане отправляет input

В POST отбражается только sumbitтоли лыжи не едут,толи

106
Скрипт типа Аккордеон на js

Скрипт типа Аккордеон на js

Подскажите пожалуйста, как мне сделать ниспадающий блок на подобие аккордеонаПытаюсь интегрировать вот такой скрипт:

106