From c573432b5b669227ead30529224551e0523c2e98 Mon Sep 17 00:00:00 2001 From: Jean-Paul Pelteret Date: Sun, 19 Apr 2020 15:11:39 +0200 Subject: [PATCH] Improve serialization of SD Expressions --- .../sd/symengine_number_types.h | 84 +++++++++++-------- 1 file changed, 50 insertions(+), 34 deletions(-) diff --git a/include/deal.II/differentiation/sd/symengine_number_types.h b/include/deal.II/differentiation/sd/symengine_number_types.h index fc3578a3e1..246f8884d9 100644 --- a/include/deal.II/differentiation/sd/symengine_number_types.h +++ b/include/deal.II/differentiation/sd/symengine_number_types.h @@ -51,6 +51,8 @@ # include # include +# include + # include # include @@ -450,11 +452,39 @@ namespace Differentiation void load(std::istream &stream); + /** + * Write the data of this object to a stream for the purpose + * of serialization. + * + * This effectively saves the value stored in this object to the + * @p archive with the given @p version number. + */ + template + void + save(Archive &archive, const unsigned int version) const; + + /** + * Read the data of this object from a stream for the purpose + * of serialization. + * + * This effectively loads into this object the value stored in of the + * @p archive with the given @p version number. + * In doing so, the previous contents of this object are thrown away. + * + * @note When deserializing a symbolic expression, it is imperative that + * you first create or deserialize all of the symbolic variables used in + * the serialized expression. + */ + template + void + load(Archive &archive, const unsigned int version); + +# ifdef DOXYGEN /** * Write and read the data of this object from a stream for the purpose * of serialization. * - * This effecively saves or loads the value stored into/out of the + * This effectively saves or loads the value stored into/out of the * @p archive with the given @p version number into this object. * If deserializing data, then the previous contents of this object * are thrown away. @@ -466,6 +496,11 @@ namespace Differentiation template void serialize(Archive &archive, const unsigned int version); +# else + // This macro defines the serialize() method that is compatible with + // the templated save() and load() method that have been implemented. + BOOST_SERIALIZATION_SPLIT_MEMBER() +# endif //@} @@ -1178,41 +1213,22 @@ namespace Differentiation template void - Expression::serialize(Archive &ar, const unsigned int /*version*/) + Expression::save(Archive &ar, const unsigned int /*version*/) const { - // This is a bit tricky... The SymEngine expression class is not - // serializable, and we're not sure if we're writing out or - // reading in here. So what we'll do is try to synchronise the - // current data with the stream, predicting if we're likely trying - // to write out data. We do this by checking if we're currently working - // with an object that has a trivial state. If not, then we're likely - // to output this object's contents. - const Expression default_constructed; - const bool likely_writing_out = - (get_RCP()->__eq__(*default_constructed.get_RCP()) == false); - std::stringstream sstream; - std::string expr = default_constructed.get_RCP()->__str__(); - - // Output - if (likely_writing_out) - { - sstream << *this; - expr = sstream.str(); - } - - // Serialise - ar &expr; - - // Input - if (!likely_writing_out) - { - sstream.clear(); - sstream << expr; - sstream >> *this; - - parse(expr); - } + sstream << *this; + const std::string expr = sstream.str(); + ar & expr; + } + + + template + void + Expression::load(Archive &ar, const unsigned int /*version*/) + { + std::string expr; + ar & expr; + parse(expr); } -- 2.39.5