hpp-util
4.12.0
Debugging tools for the HPP project.
|
Go to the documentation of this file.
19 #ifndef HPP_UTIL_SERIALIZATION_HH
20 #define HPP_UTIL_SERIALIZATION_HH
22 #include <boost/version.hpp>
23 #include <boost/archive/binary_oarchive.hpp>
24 #include <boost/archive/text_oarchive.hpp>
25 #include <boost/archive/xml_oarchive.hpp>
26 #include <boost/archive/binary_iarchive.hpp>
27 #include <boost/archive/text_iarchive.hpp>
28 #include <boost/archive/xml_iarchive.hpp>
30 #include <boost/preprocessor/comma_if.hpp>
31 #include <boost/preprocessor/facilities/is_empty.hpp>
32 #include <boost/serialization/export.hpp>
33 #include <boost/serialization/shared_ptr.hpp>
34 #include <boost/serialization/nvp.hpp>
35 #include <boost/serialization/utility.hpp>
40 #define _HPP_SERIALIZATION_SPLIT_IMPLEMENT(type,archive,arg) \
41 template void type load<archive##_iarchive>(archive##_iarchive& ar, \
42 arg BOOST_PP_COMMA_IF(BOOST_PP_NOT(BOOST_PP_IS_EMPTY(arg))) \
43 const unsigned int ver); \
44 template void type save<archive##_oarchive>(archive##_oarchive& ar, \
45 BOOST_PP_IF(BOOST_PP_IS_EMPTY(arg),,const) arg BOOST_PP_COMMA_IF(BOOST_PP_NOT(BOOST_PP_IS_EMPTY(arg))) \
46 const unsigned int ver) BOOST_PP_IF(BOOST_PP_IS_EMPTY(arg),const,)
48 #define _HPP_SERIALIZATION_IMPLEMENT(type,archive,arg) \
49 template void type serialize<archive##_iarchive>(archive##_iarchive& ar, \
50 arg BOOST_PP_COMMA_IF(BOOST_PP_NOT(BOOST_PP_IS_EMPTY(arg))) \
51 const unsigned int ver); \
52 template void type serialize<archive##_oarchive>(archive##_oarchive& ar, \
53 arg BOOST_PP_COMMA_IF(BOOST_PP_NOT(BOOST_PP_IS_EMPTY(arg))) \
54 const unsigned int ver)
56 #define HPP_SERIALIZATION_SPLIT_IMPLEMENT(type) \
57 _HPP_SERIALIZATION_SPLIT_IMPLEMENT(type::,boost::archive::xml,); \
58 _HPP_SERIALIZATION_SPLIT_IMPLEMENT(type::,boost::archive::text,); \
59 _HPP_SERIALIZATION_SPLIT_IMPLEMENT(type::,boost::archive::binary,)
61 #define HPP_SERIALIZATION_IMPLEMENT(type) \
62 _HPP_SERIALIZATION_IMPLEMENT(type::,boost::archive::xml,); \
63 _HPP_SERIALIZATION_IMPLEMENT(type::,boost::archive::text,); \
64 _HPP_SERIALIZATION_IMPLEMENT(type::,boost::archive::binary,)
66 #define HPP_SERIALIZATION_FREE_IMPLEMENT(type) \
67 namespace boost { namespace serialization { \
68 _HPP_SERIALIZATION_IMPLEMENT(,archive::xml,type& t); \
69 _HPP_SERIALIZATION_IMPLEMENT(,archive::text,type& t); \
70 _HPP_SERIALIZATION_IMPLEMENT(,archive::binary,type& t); \
73 #define HPP_SERIALIZATION_SPLIT_FREE_IMPLEMENT(type) \
74 namespace boost { namespace serialization { \
75 template<class Archive> \
76 void serialize(Archive & ar, type& t, const unsigned int version) { \
77 split_free(ar, t, version); \
79 _HPP_SERIALIZATION_IMPLEMENT(,archive::xml,type& t); \
80 _HPP_SERIALIZATION_IMPLEMENT(,archive::text,type& t); \
81 _HPP_SERIALIZATION_IMPLEMENT(,archive::binary,type& t); \
85 namespace serialization {
86 using boost::serialization::make_nvp;
87 using boost::serialization::guid;
88 using boost::serialization::guid_defined;
104 { static_assert(guid_defined<T>::value,
"You must use BOOST_CLASS_EXPORT_KEY on this class first."); }
111 std::map<std::string, holder_base*> ptrs_;
114 bool contains(
const std::string& k)
const {
return ptrs_.count(k); }
116 bool containsOfType(
const std::string& k)
const {
return (get<T>(k,
false)) != NULL; }
122 auto _ptr = ptrs_.find(k);
123 if (_ptr == ptrs_.end()) {
124 if (!throwIfNotFound)
return NULL;
125 throw std::invalid_argument(
"Pointer with name " + k +
" not found.");
127 else return _ptr->second;
130 T*
get(
const std::string& k,
bool throwIfNotFound =
false)
const {
132 if (hb == NULL)
return NULL;
134 if ((h =
dynamic_cast<holder<T>*
>(hb)) == NULL) {
135 if (!throwIfNotFound)
return NULL;
136 throw std::invalid_argument(
"Pointer with name " + k +
" found of type "
137 + hb->
classid +
" but not of requested type " + guid<T>() +
".");
142 template<
typename Base,
typename Child>
144 static_assert(guid_defined<Child>::value,
"You must use BOOST_CLASS_EXPORT_KEY on this class first.");
147 template<
typename Base,
typename Child>
148 Child*
getChildClass(
const std::string& k,
bool throwIfNotFound =
false)
const {
150 if (hb == NULL)
return NULL;
153 if (!throwIfNotFound)
return NULL;
154 throw std::invalid_argument(
"Pointer with name " + k +
" found of type "
155 + hb->
classid +
" but not of requested type " + guid<Child>() +
".");
159 if (!throwIfNotFound)
return NULL;
160 throw std::invalid_argument(
"Pointer with name " + k +
" found of type "
161 + hb->
classid +
" but not of requested type " + guid<Child>() +
".");
167 for (
auto it : ptrs_)
delete it.second;
171 template<
typename Archive, std::enable_if_t<Archive::is_saving::value,
int> = 42>
174 auto size (ptrs_.size());
175 ar << make_nvp(
"nrequires", size);
176 typedef std::pair<std::string,std::string> string_pair;
177 for (
auto it : ptrs_) {
178 string_pair requires(it.first, it.second->classid);
179 ar << make_nvp(
"requires", requires);
182 template<
typename Archive, std::enable_if_t<!Archive::is_saving::value,
int> = 42>
185 decltype(ptrs_.size()) size;
186 ar >> make_nvp(
"nrequires", size);
187 typedef std::pair<std::string,std::string> string_pair;
189 for (decltype(size) i = 0; i < size; ++i) {
190 ar >> make_nvp(
"requires", pair);
192 if (pair.second != hb->
classid)
193 throw std::invalid_argument(
"Required pointer with name " + pair.first +
" found of type "
194 + hb->
classid +
" but not of required type " + pair.second +
".");
199 template<
typename archive_base,
typename... parent_classes>
205 initialize_tpl<archive_base>(*
this);
208 using archive_base::archive_base;
211 template<
typename Archive>
213 template<
typename Archive>
227 #endif // HPP_UTIL_SERIALIZATION_HH
holder(T *t, const char *classid)
Definition: serialization.hh:102
bool contains(const std::string &k) const
Definition: serialization.hh:114
archive_ptr_holder & cast(Archive &ar)
Definition: serialization.hh:212
void insert(const std::string &k, holder_base *ptr)
Definition: serialization.hh:118
void insertChildClass(const std::string &k, Child *ptr)
Definition: serialization.hh:143
void initialize_tpl(Archive &ar)
Definition: serialization.hh:172
void initialize()
Definition: serialization.hh:203
archive_tpl< boost::archive::text_oarchive > text_oarchive
Definition: serialization.hh:223
T * get(const std::string &k, bool throwIfNotFound=false) const
Definition: serialization.hh:130
archive_tpl< boost::archive::binary_iarchive > binary_iarchive
Definition: serialization.hh:216
bool containsOfType(const std::string &k) const
Definition: serialization.hh:116
void insert(const std::string &k, T *ptr)
Definition: serialization.hh:120
Child * getChildClass(const std::string &k, bool throwIfNotFound=false) const
Definition: serialization.hh:148
virtual ~holder_base()=default
holder_base(const char *classid)
Definition: serialization.hh:96
Definition: serialization.hh:99
Definition: assertion.hh:22
T * t
Definition: serialization.hh:101
archive_tpl< boost::archive::binary_oarchive > binary_oarchive
Definition: serialization.hh:217
Definition: serialization.hh:109
Definition: serialization.hh:200
archive_tpl< boost::archive::text_iarchive > text_iarchive
Definition: serialization.hh:222
Definition: serialization.hh:90
archive_tpl< boost::archive::xml_oarchive > xml_oarchive
Definition: serialization.hh:220
virtual ~archive_ptr_holder()
Definition: serialization.hh:166
holder_base * get(const std::string &k, bool throwIfNotFound=false) const
Definition: serialization.hh:121
holder(T *t)
Definition: serialization.hh:103
const char * classid
Definition: serialization.hh:92
archive_tpl< boost::archive::xml_iarchive > xml_iarchive
Definition: serialization.hh:219