Завершено
3
05.09.2017, 08:57
03.10.2017, 10:46
Реализовать фреймворк для бинарной сериализации и десериализации произвольных структур данных.
Основа фреймворка приведена ниже:
// serialize.h
#pragma once
#include <iostream>
#include <iterator>
#include <algorithm>
template <typename T>
struct serializer {
    static void apply(const T &obj, std::ostream &os) {
        const uint8_t *ptr = reinterpret_cast<const uint8_t *>(&obj);
        std::ostream_iterator<uint8_t> oi(os);
        std::copy(ptr, ptr + sizeof(T), oi);
    }
};
///////////////////////////////////////////////////////////////////////
template <typename T>
struct deserializer {
    static void apply(T &val, std::istream &is) {
        uint8_t *ptr = reinterpret_cast<uint8_t*>(&val);
        std::istream_iterator<uint8_t> ii(is);
        std::copy_n(ii, sizeof(T), ptr);
    }
};
///////////////////////////////////////////////////////////////////////
template <typename T>
void serialize(const T &obj, std::ostream &os)
{
    serializer<T>::apply(obj, os);
}
template <typename T>
void deserialize(T &obj, std::istream &is)
{
    return deserializer<T>::apply(obj, is);
}
Данный код позволяет сериализовывать и десериализовывать любые примитивные объекты, как показано в примере:
// test_serialize.cpp
#include <fstream>
#include <iostream>
#include "serialize.h"
using namespace std;
int main()
{
    ofstream ofs("test.ser", ofstream::out | ofstream::binary);
    char hello[7] = "hello!";
    int boo[3] = { 1, 2, 3 };
    serialize(hello, ofs);
    serialize(boo, ofs);
    char hello2[7];
    int boo2[3];
    ofs.close();
    ifstream ifs("test.ser", ifstream::in | ofstream::binary);
    ifs >> noskipws;
    deserialize(hello2, ifs);
    deserialize(boo2, ifs);
    if (equal(hello, hello + 7, hello2))
        cout << "Hello OK!" << endl;
    if (equal(boo, boo + 3, boo2))
        cout << "Boo OK!" << endl;
    return 0;
}
Требуется расширить поведение serialize и deserialize, чтобы они поддерживали сериализацию и десериализацию стандартных классов и контейнеров:
std::string.vector<T> для любого сериализуемого типа T.map<K, V> для любых сериализуемых типов K, V.