Skip to content

Instantly share code, notes, and snippets.

@motonacciu
Last active December 17, 2015 10:48
Show Gist options
  • Select an option

  • Save motonacciu/5597021 to your computer and use it in GitHub Desktop.

Select an option

Save motonacciu/5597021 to your computer and use it in GitHub Desktop.
namespace detail {
template <class T>
class serialize_helper;
template <class T>
void serializer(const T& obj, StreamType::iterator&);
template <class tuple_type>
inline void serialize_tuple(const tuple_type& obj, StreamType::iterator& res, int_<0>) {
constexpr size_t idx = std::tuple_size<tuple_type>::value-1;
serializer(std::get<idx>(obj), res);
}
template <class tuple_type, size_t pos>
inline void serialize_tuple(const tuple_type& obj, StreamType::iterator& res, int_<pos>) {
constexpr size_t idx = std::tuple_size<tuple_type>::value-pos-1;
serializer(std::get<idx>(obj), res);
// recur
serialize_tuple(obj, res, int_<pos-1>());
}
template <class... T>
struct serialize_helper<std::tuple<T...>> {
static void apply(const std::tuple<T...>& obj, StreamType::iterator& res) {
detail::serialize_tuple(obj, res, detail::int_<sizeof...(T)-1>());
}
};
template <>
struct serialize_helper<std::string> {
static void apply(const std::string& obj, StreamType::iterator& res) {
// store the number of elements of this string at the beginning
serializer(obj.length(), res);
for(const auto& cur : obj) { serializer(cur, res); }
}
};
template <class T>
struct serialize_helper<std::vector<T>> {
static void apply(const std::vector<T>& obj, StreamType::iterator& res) {
// store the number of elements of this vector at the beginning
serializer(obj.size(), res);
for(const auto& cur : obj) { serializer(cur, res); }
}
};
template <class T>
struct serialize_helper {
static void apply(const T& obj, StreamType::iterator& res) {
const uint8_t* ptr = reinterpret_cast<const uint8_t*>(&obj);
std::copy(ptr,ptr+sizeof(T),res);
res+=sizeof(T);
}
};
template <class T>
inline void serializer(const T& obj, StreamType::iterator& res) {
serialize_helper<T>::apply(obj,res);
}
} // end detail namespace
template <class T>
inline void serialize(const T& obj, StreamType& res) {
size_t offset = res.size();
size_t size = get_size(obj);
res.resize(res.size() + size);
StreamType::iterator it = res.begin() + offset;
detail::serializer(obj,it);
assert(res.begin() + offset + size == it);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment