How to de/serialize a map with template class using boost::multiprecision::mpq_rational

前端 未结 1 874
孤城傲影
孤城傲影 2020-12-21 23:18

I have the following template class:

#include 
#include 
#include 
#include 

        
1条回答
  •  青春惊慌失措
    2020-12-22 00:05

    There's passthrough support for Boost Multiprecision serialization:

    Classes number, debug_adaptor, logged_adaptor and rational_adaptor have "pass through" serialization support which requires the underlying backend to be serializable.

    Backends cpp_int, cpp_bin_float, cpp_dec_float and float128 have full support for Boost.Serialization.

    That is to say, it's supported iff the backend supports it: mailing list:

    > Does/will multiprecesion have support for boost::serialization?

    Good question, and no not yet. I guess it should do though... it's hard though as some backends (for example GMP's mpf_t) don't round trip to and from string representations, and have an internal structure that probably shouldn't be relied upon :-

    You can:

    • use cpp_rational (as it is supported implicitly by the above doc excerpt)
    • use Boost Rational: How to serialize boost::rational
    • use raw mpz_* API to serialize, see e.g. How to serialize a GMP rational number?

    • you can explicitly add serialization support for the backend (note that using the gmp API's will be more efficient)

      namespace boost { namespace serialization {
      
          template 
              void save(Archive& ar, ::boost::multiprecision::backends::gmp_rational const& r, unsigned /*version*/)
              {
                  std::string tmp = r.str(10000, std::ios::fixed);
                  ar & tmp;
              }
      
          template 
              void load(Archive& ar, ::boost::multiprecision::backends::gmp_rational& r, unsigned /*version*/)
              {
                  std::string tmp;
                  ar & tmp;
                  r = tmp.c_str();
              }
      
      } }
      
      BOOST_SERIALIZATION_SPLIT_FREE(::boost::multiprecision::backends::gmp_rational)
      

    Here's a demo Live On Coliru with a simple roundtrip test.

    Full Listing

    #include 
    #include 
    #include 
    #include 
    #include 
    #include 
    
    namespace boost { namespace serialization {
    
        template 
            void save(Archive& ar, ::boost::multiprecision::backends::gmp_rational const& r, unsigned /*version*/)
            {
                std::string tmp = r.str(10000, std::ios::fixed);
                ar & tmp;
            }
    
        template 
            void load(Archive& ar, ::boost::multiprecision::backends::gmp_rational& r, unsigned /*version*/)
            {
                std::string tmp;
                ar & tmp;
                r = tmp.c_str();
            }
    
    } }
    
    BOOST_SERIALIZATION_SPLIT_FREE(::boost::multiprecision::backends::gmp_rational)
    
    #include 
    #include 
    #include 
    #include 
    #include 
    #include 
    
    template 
    class A {
        friend class boost::serialization::access;
        template
            void serialize(Archive & ar, const unsigned int version)
            {
                ar & a;
            }
    
      public:
        T a;
        bool operator<(A const& o) const { return a
    
    using KeyElement = boost::multiprecision::mpq_rational;
    using Key        = A >;
    using Data       = std::map;
    
    int main()
    {
        std::stringstream ss;
        {
            Data mmm { 
                { Key {{{KeyElement { 1, 2 }, KeyElement { 3, 4 }} }}, 5 }, 
                { Key {{{KeyElement { 6, 7 }, KeyElement { 8, 9 }} }}, 42 },
            };
            boost::archive::text_oarchive oa(ss);
    
            oa << mmm;
        }
    
        std::cout << "Serialized:\t" << ss.str() << "\n";
    
        {
            boost::archive::text_iarchive iarch(ss);
            Data mmm; 
            iarch >> mmm;
    
            std::cout << "Roundtrip:\t";
            boost::archive::text_oarchive oa(std::cout);
            oa << mmm;
        }
    }
    

    0 讨论(0)
提交回复
热议问题