Vector С++

Вообще уже не понимаю, что нужно делать. Написал какую-то чушь. Ничего не работает. В текстовый файл пишет неправильно, с бинарным вообще непонятно. Если вам не сложно, посмотрите пожалуйста и скажите, что нужно сделать, чтобы оно читалось и записывалось нормально. У меня ступор с этим заданием какой-то.

#include<iostream>
#include<string>
#include<fstream>
#include<vector>

using namespace std;

class Phone_book
{
	static int s_id;
	string id;
	string name;
	string surname;
	string adds;
	string number;
	static void save(const string& str, fstream& fs)
	{
		size_t len = str.size();
		fs.write((const char*)&len, sizeof(size_t));
		fs.write(str.data(), len);
	}
	static void load(string& str, fstream& fs)
	{
		size_t len;
		fs.read((char*)&len, sizeof(size_t));
		char* string = new char[len + 1];
		fs.read(string, len);
		str[len] = 0;
		str = string;
		delete[] string;
	}
public:
	Phone_book(const char* id = "", const char* name = "", const char* surname = "", const char* adds = "", const char* number = "")
	{
		this->id = id;
		this->name = name;
		this->surname = surname;
		this->adds = adds;
		this->number = number;
	}
	const string& getID()const
	{
		return id;
	}
	const string& getName()const
	{
		return name;
	}
	const string& getSurname()const
	{
		return surname;
	}
	const string& getAddress()const
	{
		return adds;
	}
	const string& getNumber()const
	{
		return number;
	}
	void setID(const string& id)
	{
		this->id = id;
	}
	void setName(const string& name)
	{
		this->name = name;
	}
	void setSurname(const string& surname)
	{
		this->surname = surname;
	}
	void setAddress(const string& adds)
	{
		this->adds = adds;
	}
	void setNumber(const string& number)
	{
		this->number = number;
	}
	void setContact()
	{
		cout << "Enter contact details: " << endl;
		cout << "Name: " << endl; getline(cin, name);
		cout << "Surname: " << endl; getline(cin, surname);
		cout << "Address: " << endl; getline(cin, adds);
		cout << "Phone Number: " << endl; getline(cin, number);
	}
	void write(fstream& fs) const
	{
		save(id, fs);
		save(name, fs);
		save(surname, fs);
		save(adds, fs);
		save(number, fs);
	}
	void read(fstream& fs)
	{
		load(id, fs);
		load(name, fs);
		load(surname, fs);
		load(adds, fs);
		load(number, fs);
	}
	void show()
	{		
		cout << id << " " << name << " " << surname << " " << adds << " " << number << endl;		
	}
	friend ostream& operator << (fstream& fs, const Phone_book& ph)
	{
		return fs << ph.id << " " << ph.name << " " << ph.surname << " " << ph.adds << " " << ph.number;
	}
};
int main()
{
	static int s_id = 1;
	vector<Phone_book>contacts;
	Phone_book obj;
	string res;
	fstream fs;
	bool exit = true;
	int action = 0;
	do
	{
		obj.setContact();
		obj.setID(to_string(s_id));
		s_id++;
		contacts.push_back(obj);
		cout << "Enter new data(1 - Yes, 0 - No)\n";
		cin >> exit;
		cin.get();
	} while (exit);
	do
	{
		if (exit == false)
		{
			cout << "Select action: " << endl;
			cout << "1. Delete contact;" << endl;
			cout << "2. Save information about phone contacts to text file" << endl;
			cout << "3. Save information about phone contacts to binary file" << endl;
			cout << "4. Load information about phone contacts from text file;" << endl;
			cout << "5. Load information about phone contacts from binary file;" << endl;
			cout << "6. Exit the program." << endl;
			cin >> action;
			cin.get();
			if (action == 1)
			{
				int pos;
				for (int i = 0; i < contacts.size(); i++)
				{
					cout << "Position " << i << ": ";
					contacts[i].show();
				}
				cout << "Enter the position of the contact you want delete:" << endl;
				cin >> pos;
				if (pos > contacts.size() - 1 || pos < 0)
					cout << "Wrong position" << endl;
				else
				{
					contacts.erase(contacts.begin() + pos);

				}
				for (int i = 0; i < contacts.size(); i++)
				{
					contacts[i].show();
				}
			}
			else if (action == 2)
			{
				res = obj.getID() + " " + obj.getName() + " " + obj.getSurname() + " " + obj.getAddress() + " " + obj.getNumber();
				try
				{
					fs.open("Phone_book.txt", ios::ate|ios::out);
					if (!fs.is_open())
						throw logic_error("Phone_book.txt can not be opened");
					fs << res << endl;
					fs.close();
				}
				catch (logic_error & ex)
				{
					cerr << "Error: " << ex.what() << endl;
				}
			}
			else if (action == 3)
			{
				fstream fs("Phone_book.bin", ios::out | ios::binary);
				for (int i = 0; i < contacts.size(); i++)
				{
					contacts[i].write(fs);
				}
			}
			else if (action == 4)
			{
				fstream fs("Phone_book.txt", ios::in);
				string s;
				while (getline(fs, s))
				{
					cout << s << endl;
				}
				fs.close();
			}
			else if (action == 5)
			{
				vector<Phone_book>cont;
				Phone_book obj2;
				fstream fs("Phone_book.bin", ios::in | ios::binary);
				if (fs.is_open())
				{
					while (!fs.eof())
					{
						obj2.read(fs);
						cont.push_back(obj2);
					}	
				}
				for (int i = 0; i < cont.size(); ++i)
				{
					cont[i].show();
				}
			}
			else if (action<1||action>6)
				cout << "Wrong choice!" << endl;			
		}

	} while (action != 6);
	
	return 0;
}

А что пишет?

И в нем что получается? Можно посмотреть любым HEX-редактором (чтобы было проще смотреть — вводить только англ. буквы). Строки тут пишутся в виде размер (4 байта, или 8 если 64 бит) + символы.

Если это запись в текстовый файл, то непонятно где чтение.
И я бы не парился с операторами, а просто сделал функции типа writeToBinFile, readFromBinFile, writeToTextFile, readFromTextFile. Иначе например непонятно чем один вид файлов (и надо помнить какой из них) заслужил операторы.

1 vasya pupkin street 36925874 2 elenaa ivanova avenua 3698524

Вот что записывается в бинарник (я записал два значения), а при выводе вылетает все.
В текстовый из двух записей записывается только последний контакт и в консоль выводится соответственно он же.

Так а тут и записывается один последний, а не все.

Почему-то странные символы в виде прямоугольников тут пропадают

Тут 0 не туда присваивается, в примере ж было

Чтобы не путаться я бы переименовал переменную, в которую из файла чтение, в например strBytes

Я понимаю как это должно происходить в массиве, с вектором не могу понять вообще.

for (int i = 0; i < 12; ++i)
			{
				str[i] = "Some text ";
				fs << str[i] << endl;
			}

Как это организовать в векторе?

Так же как с бин?)


Код всё еще зачем-то путает читателей, говорит, что в массиве хранятся телефонные книги, а не контакты.

Я совсем запутался и ничего не понимаю уже

Если я так же запишу, то запишутся непонятные символы и выведутся на экран

Ну дык для текстового надо вызывать функцию записи текста, а не бин.

Если бы еще бинарник заработал

С текстовым вроде разобрался. Сам себя запутал просто

try
				{
					fs.open("Phone_book.txt", ios::out);
					if (!fs.is_open())
						throw logic_error("Phone_book.txt can not be opened");
					for (int i = 0; i < contacts.size(); i++)
					{
						fs << contacts[i] << endl;
					}
					fs.close();
				}
				catch (logic_error & ex)
				{
					cerr << "Error: " << ex.what() << endl;
				}

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

Потому что надо смотреть не текстовым редактором, а

https://www.google.com/search?q=hex+editor

#35 исправлено?

вроде исправил

static void load(string& str, fstream& fs)
	{
		size_t len;
		fs.read((char*)&len, sizeof(size_t));
		char* buf = new char[len + 1];
		fs.read(buf, len);
		buf[len] = 0;
		str = buf;
		delete[] buf;
	}

но оно все равно не работает

Так а с какой ошибкой и где вылетает?

Не понимаю, что не так

len некорректный по каким-то причинам.

Я бы для начала определил на каком этапе это происходит с помощью отладчика или отладочного вывода (например, выводить прочитанные значения в load).

Так вот, я сделал cout << id << name << surname << adds << number << endl; Оно вывелось на экран и слетело