1 #ifndef SYMENGINE_SERIALIZE_CEREAL_H
2 #define SYMENGINE_SERIALIZE_CEREAL_H
11 #include <symengine/utilities/stream_fmt.h>
13 #include <cereal/cereal.hpp>
14 #include <cereal/version.hpp>
15 #include <cereal/types/polymorphic.hpp>
16 #include <cereal/types/string.hpp>
17 #include <cereal/details/helpers.hpp>
18 #include <cereal/types/map.hpp>
19 #include <cereal/types/unordered_map.hpp>
20 #include <cereal/types/set.hpp>
21 #include <cereal/types/vector.hpp>
22 #include <cereal/types/utility.hpp>
23 #include <cereal/archives/portable_binary.hpp>
28 template <
class Archive>
31 using Archive::Archive;
34 void save_rcp_basic(
const RCP<const Basic> &ptr)
36 uintptr_t addr = (uintptr_t)(
void *)ptr.get();
39 auto id = _addresses.find(addr);
40 uint8_t first_seen = (
id == _addresses.end());
51 _keep_alive.push_back(ptr);
52 TypeID type_code = ptr->get_type_code();
53 save_typeid(*
this, type_code);
55 #define SYMENGINE_ENUM(type, Class) \
57 save_basic(*this, static_cast<const Class &>(*ptr)); \
59 #include "symengine/type_codes.inc"
62 save_basic(*
this, *ptr);
64 _addresses.insert(addr);
68 std::set<uintptr_t> _addresses;
69 std::vector<RCP<const Basic>> _keep_alive;
74 template <
class Archive>
77 using Archive::Archive;
81 RCP<const T> load_rcp_basic()
90 if (first_seen >= 2) {
91 throw SerializationError(
"Invalid input");
95 auto it = _rcp_map.find(addr);
96 if (it == _rcp_map.end()) {
97 throw SerializationError(
"Invalid shared pointer");
99 RCP<const Basic> b = it->second;
100 switch (b->get_type_code()) {
101 #define SYMENGINE_ENUM(type_enum, Class) \
103 if (not std::is_base_of<T, Class>::value) { \
104 throw SerializationError("Cannot convert to given type"); \
106 return rcp_static_cast<const T>(b); \
109 #include "symengine/type_codes.inc"
110 #undef SYMENGINE_ENUM
112 throw SerializationError(
"Unknown typeID");
117 load_typeid(*
this, type_code);
119 #define SYMENGINE_ENUM(type_enum, Class) \
121 RCP<const Class> dummy_ptr; \
122 RCP<const Basic> basic_ptr = load_basic(*this, dummy_ptr); \
123 _rcp_map[addr] = basic_ptr; \
124 if (not std::is_base_of<T, Class>::value) { \
125 throw SerializationError("Cannot convert to given type"); \
127 return rcp_static_cast<const T>(basic_ptr); \
130 #include "symengine/type_codes.inc"
131 #undef SYMENGINE_ENUM
133 throw SerializationError(
"Unknown typeID");
135 }
catch (cereal::Exception &e) {
136 throw SerializationError(e.what());
141 std::unordered_map<uintptr_t, RCP<const Basic>> _rcp_map;
146 template <
class Archive>
147 inline void save_basic(Archive &ar,
const Basic &b)
149 const auto t_code = b.get_type_code();
150 throw SerializationError(StreamFmt()
151 << __FILE__ <<
":" << __LINE__
153 <<
": " << __PRETTY_FUNCTION__
155 <<
" not supported: " << type_code_name(t_code)
156 <<
" (" << t_code <<
")"
158 <<
", " << b.__str__()
162 template <
class Archive>
163 inline void save_basic(Archive &ar,
const Symbol &b)
167 template <
class Archive>
168 inline void save_basic(Archive &ar,
const Dummy &b)
170 ar(b.get_name(), b.get_index());
172 template <
class Archive>
173 inline void save_basic(Archive &ar,
const Mul &b)
178 template <
class Archive>
179 inline void save_basic(Archive &ar,
const Add &b)
184 template <
class Archive>
185 inline void save_basic(Archive &ar,
const Pow &b)
190 template <
typename Archive>
191 void save_helper(Archive &ar,
const integer_class &intgr)
193 std::ostringstream s;
197 template <
typename Archive>
198 void save_helper(Archive &ar,
const rational_class &rat)
200 integer_class num = get_num(rat);
201 integer_class den = get_den(rat);
202 save_helper(ar, num);
203 save_helper(ar, den);
205 template <
typename Archive>
206 void save_helper(Archive &ar,
const Expression &c)
210 template <
typename Archive,
typename Container>
211 void save_poly_dict(Archive &ar,
const Container &c)
214 for (
const auto &term : c.dict_) {
216 save_helper(ar, term.second);
219 template <
typename Archive>
220 void save_basic(Archive &ar,
const UIntPoly &b)
223 save_poly_dict(ar, b.get_poly());
225 template <
typename Archive>
226 void save_basic(Archive &ar,
const URatPoly &b)
229 save_poly_dict(ar, b.get_poly());
231 template <
typename Archive>
232 void save_basic(Archive &ar,
const UExprPoly &b)
235 save_poly_dict(ar, b.get_poly());
237 template <
typename Archive>
238 void save_basic(Archive &ar,
const MIntPoly &b)
241 save_poly_dict(ar, b.get_poly());
243 template <
typename Archive>
244 void save_basic(Archive &ar,
const MExprPoly &b)
247 save_poly_dict(ar, b.get_poly());
249 #if defined(HAVE_SYMENGINE_FLINT) || defined(HAVE_SYMENGINE_PIRANHA)
250 template <
typename Archive,
typename Poly>
251 void save_dense_poly(Archive &ar,
const Poly &b)
254 unsigned int size =
static_cast<unsigned int>(b.size());
256 for (
unsigned int i = 0; i < size; ++i) {
257 save_helper(ar, b.get_coeff(i));
261 #ifdef HAVE_SYMENGINE_FLINT
262 template <
typename Archive>
263 void save_basic(Archive &ar,
const UIntPolyFlint &b)
265 save_dense_poly(ar, b);
267 template <
typename Archive>
268 void save_basic(Archive &ar,
const URatPolyFlint &b)
270 save_dense_poly(ar, b);
273 #ifdef HAVE_SYMENGINE_PIRANHA
274 template <
typename Archive>
275 void save_basic(Archive &ar,
const UIntPolyPiranha &b)
277 save_dense_poly(ar, b);
279 template <
typename Archive>
280 void save_basic(Archive &ar,
const URatPolyPiranha &b)
282 save_dense_poly(ar, b);
285 template <
class Archive>
286 inline void save_basic(Archive &ar,
const Integer &b)
290 template <
class Archive>
291 inline void save_basic(Archive &ar,
const RealDouble &b)
295 template <
class Archive>
296 inline void save_basic(Archive &ar,
const Rational &b)
298 ar(b.get_num(), b.get_den());
300 template <
class Archive>
301 inline void save_basic(Archive &ar,
const ComplexBase &b)
303 ar(b.real_part(), b.imaginary_part());
305 template <
class Archive>
306 inline void save_basic(Archive &ar,
const Interval &b)
308 ar(b.get_left_open(), b.get_start(), b.get_right_open(), b.get_end());
310 template <
class Archive>
311 inline void save_basic(Archive &ar,
const BooleanAtom &b)
315 template <
class Archive>
316 inline void save_basic(Archive &ar,
const Infty &b)
318 ar(b.get_direction());
321 template <
class Archive>
322 inline void save_basic(Archive &ar,
const NaN &b)
326 template <
class Archive>
327 inline void save_basic(Archive &ar,
const Constant &b)
331 template <
class Archive>
332 inline void save_basic(Archive &ar,
const OneArgFunction &b)
336 template <
class Archive>
337 inline void save_basic(Archive &ar,
const TwoArgFunction &b)
339 ar(b.get_arg1(), b.get_arg2());
342 template <
class Archive>
343 inline void save_basic(Archive &ar,
const Relational &b)
345 ar(b.get_arg1(), b.get_arg2());
347 template <
class Archive>
348 inline void save_basic(Archive &ar,
const And &b)
350 ar(b.get_container());
352 template <
class Archive>
353 inline void save_basic(Archive &ar,
const Or &b)
355 ar(b.get_container());
357 template <
class Archive>
358 inline void save_basic(Archive &ar,
const Xor &b)
360 ar(b.get_container());
362 template <
class Archive>
363 inline void save_basic(Archive &ar,
const Not &b)
367 template <
class Archive>
368 inline void save_basic(Archive &ar,
const Contains &b)
370 ar(b.get_expr(), b.get_set());
372 template <
class Archive>
373 inline void save_basic(Archive &ar,
const Piecewise &b)
377 template <
class Archive>
378 inline void save_basic(Archive &ar,
const Reals &b)
381 template <
class Archive>
382 inline void save_basic(Archive &ar,
const Rationals &b)
385 template <
class Archive>
386 inline void save_basic(Archive &ar,
const EmptySet &b)
389 template <
class Archive>
390 inline void save_basic(Archive &ar,
const Integers &b)
393 template <
class Archive>
394 inline void save_basic(Archive &ar,
const UniversalSet &b)
397 template <
class Archive>
398 inline void save_basic(Archive &ar,
const Union &b)
400 ar(b.get_container());
402 template <
class Archive>
403 inline void save_basic(Archive &ar,
const Complement &b)
405 ar(b.get_universe(), b.get_container());
407 template <
class Archive>
408 inline void save_basic(Archive &ar,
const ImageSet &b)
410 ar(b.get_symbol(), b.get_expr(), b.get_baseset());
412 template <
class Archive>
413 inline void save_basic(Archive &ar,
const FiniteSet &b)
415 ar(b.get_container());
417 template <
class Archive>
418 inline void save_basic(Archive &ar,
const ConditionSet &b)
420 ar(b.get_symbol(), b.get_condition());
422 #ifdef HAVE_SYMENGINE_MPFR
423 template <
class Archive>
424 inline void save_basic(Archive &ar,
const RealMPFR &b)
426 ar(b.__str__(), b.get_prec());
429 template <
class Archive>
430 inline void save_basic(Archive &ar,
const GaloisField &b)
432 throw NotImplementedError(
"GaloisField saving is not implemented yet.");
434 template <
class Archive>
435 inline void save_basic(Archive &ar,
const SeriesCoeffInterface &)
437 throw NotImplementedError(
"Series saving is not implemented yet.");
439 template <
class Archive>
440 inline void save_basic(Archive &ar,
const MultiArgFunction &b)
444 template <
class Archive>
445 inline void save_basic(Archive &ar,
const FunctionSymbol &b)
447 ar(b.get_name(), b.get_args());
449 template <
class Archive>
450 inline void save_basic(Archive &ar,
const Derivative &b)
452 ar(b.get_arg(), b.get_symbols());
454 template <
class Archive>
455 inline void save_basic(Archive &ar,
const Subs &b)
457 ar(b.get_arg(), b.get_dict());
459 template <
class Archive>
460 inline void save_basic(Archive &ar,
const NumberWrapper &b)
462 throw NotImplementedError(
"NumberWrapper saving is not implemented yet.");
464 template <
class Archive>
465 inline void save_basic(Archive &ar,
const FunctionWrapper &b)
467 throw NotImplementedError(
"FunctionWrapper saving is not implemented yet.");
471 template <
class Archive,
class T>
477 throw SerializationError(
"Need a RCPBasicAwareOutputArchive");
479 ar_ptr->save_rcp_basic(rcp_static_cast<const Basic>(ptr));
481 template <
class Archive>
482 RCP<const Basic> load_basic(Archive &ar, RCP<const RealDouble> &)
486 return real_double(val);
488 template <
class Archive>
489 RCP<const Basic> load_basic(Archive &ar, RCP<const Infty> &)
491 RCP<const Number> direction;
493 return Infty::from_direction(direction);
495 template <
class Archive>
496 RCP<const Basic> load_basic(Archive &ar, RCP<const NaN> &)
498 return rcp_static_cast<const Basic>(Nan);
500 template <
class Archive>
501 RCP<const Basic> load_basic(Archive &ar, RCP<const Symbol> &)
507 template <
class Archive>
508 RCP<const Basic> load_basic(Archive &ar, RCP<const Dummy> &)
513 return dummy(name, index);
515 template <
class Archive>
516 RCP<const Basic> load_basic(Archive &ar, RCP<const Mul> &)
518 RCP<const Number> coeff;
519 map_basic_basic dict;
522 return make_rcp<const Mul>(coeff, std::move(dict));
524 template <
class Archive>
525 RCP<const Basic> load_basic(Archive &ar, RCP<const Add> &)
527 RCP<const Number> coeff;
531 return make_rcp<const Add>(coeff, std::move(dict));
533 template <
class Archive>
534 RCP<const Basic> load_basic(Archive &ar, RCP<const Pow> &)
536 RCP<const Basic> base,
exp;
539 return make_rcp<const Pow>(base,
exp);
541 template <
typename Archive>
542 void load_helper(Archive &ar, integer_class &intgr)
546 if (int_str.size() == 0) {
547 throw SerializationError(
"invalid integer");
549 if (not(int_str[0] ==
'-' or std::isdigit(int_str[0]))) {
550 throw SerializationError(
"invalid integer");
552 for (
auto it = ++int_str.begin(); it < int_str.end(); it++) {
553 if (not std::isdigit(*it)) {
554 throw SerializationError(
"invalid integer");
557 intgr = integer_class(std::move(int_str));
559 template <
typename Archive>
560 void load_helper(Archive &ar, rational_class &rat)
562 integer_class num, den;
563 load_helper(ar, num);
564 load_helper(ar, den);
565 rat = rational_class(num, den);
567 template <
typename Archive>
568 void load_helper(Archive &ar, Expression &c)
572 c = Expression(std::move(b));
574 template <
typename RawDict,
typename Archive>
575 RawDict load_poly_dict(Archive &ar)
580 for (
size_t i = 0; i < size; ++i) {
581 typename RawDict::key_type exponent;
582 typename RawDict::mapped_type coeff;
584 load_helper(ar, coeff);
585 dict.emplace(std::move(exponent), std::move(coeff));
589 template <
typename Archive>
590 RCP<const Basic> load_basic(Archive &ar, RCP<const UIntPoly> &)
592 RCP<const Basic> var;
594 return make_rcp<const UIntPoly>(var,
595 UIntDict(load_poly_dict<map_uint_mpz>(ar)));
597 template <
typename Archive>
598 RCP<const Basic> load_basic(Archive &ar, RCP<const URatPoly> &)
600 RCP<const Basic> var;
602 return make_rcp<const URatPoly>(var,
603 URatDict(load_poly_dict<map_uint_mpq>(ar)));
605 template <
typename Archive>
606 RCP<const Basic> load_basic(Archive &ar, RCP<const UExprPoly> &)
608 RCP<const Basic> var;
610 return make_rcp<const UExprPoly>(
611 var, UExprDict(load_poly_dict<map_int_Expr>(ar)));
613 template <
typename Archive>
614 RCP<const Basic> load_basic(Archive &ar, RCP<const MIntPoly> &)
618 auto dict = load_poly_dict<umap_uvec_mpz>(ar);
619 return MIntPoly::from_container(
620 vars, MIntDict(std::move(dict),
static_cast<unsigned>(vars.size())));
622 template <
typename Archive>
623 RCP<const Basic> load_basic(Archive &ar, RCP<const MExprPoly> &)
627 auto dict = load_poly_dict<umap_vec_expr>(ar);
628 return MExprPoly::from_container(
629 vars, MExprDict(std::move(dict),
static_cast<unsigned>(vars.size())));
631 #if defined(HAVE_SYMENGINE_FLINT) || defined(HAVE_SYMENGINE_PIRANHA)
632 template <
typename Poly,
typename Cf,
typename Archive>
633 RCP<const Basic> load_dense_poly(Archive &ar)
635 RCP<const Basic> var;
638 std::map<unsigned, Cf> dict;
639 for (
unsigned int i = 0; i < size; ++i) {
641 load_helper(ar, coeff);
642 dict.emplace(i, std::move(coeff));
644 return Poly::from_dict(var, std::move(dict));
647 #ifdef HAVE_SYMENGINE_FLINT
648 template <
typename Archive>
649 RCP<const Basic> load_basic(Archive &ar, RCP<const UIntPolyFlint> &)
651 return load_dense_poly<UIntPolyFlint, integer_class>(ar);
653 template <
typename Archive>
654 RCP<const Basic> load_basic(Archive &ar, RCP<const URatPolyFlint> &)
656 return load_dense_poly<URatPolyFlint, rational_class>(ar);
659 #ifdef HAVE_SYMENGINE_PIRANHA
660 template <
typename Archive>
661 RCP<const Basic> load_basic(Archive &ar, RCP<const UIntPolyPiranha> &)
663 return load_dense_poly<UIntPolyPiranha, integer_class>(ar);
665 template <
typename Archive>
666 RCP<const Basic> load_basic(Archive &ar, RCP<const URatPolyPiranha> &)
668 return load_dense_poly<URatPolyPiranha, rational_class>(ar);
671 template <
class Archive>
672 RCP<const Basic> load_basic(Archive &ar, RCP<const Integer> &)
678 template <
class Archive>
679 RCP<const Basic> load_basic(Archive &ar, RCP<const Constant> &)
685 template <
class Archive>
686 RCP<const Basic> load_basic(Archive &ar, RCP<const Rational> &)
688 RCP<const Integer> num, den;
692 template <
class Archive>
693 RCP<const Basic> load_basic(Archive &ar, RCP<const Complex> &)
695 RCP<const Number> num, den;
699 template <
class Archive,
class T>
701 load_basic(Archive &ar, RCP<const T> &,
702 typename std::enable_if<std::is_base_of<ComplexBase, T>::value,
703 int>::type * =
nullptr)
705 RCP<const Number> num, den;
709 template <
class Archive>
710 RCP<const Basic> load_basic(Archive &ar, RCP<const Interval> &)
712 RCP<const Number> start, end;
713 bool left_open, right_open;
714 ar(left_open, start, right_open, end);
715 return make_rcp<const Interval>(start, end, left_open, right_open);
717 template <
class Archive>
718 RCP<const Basic> load_basic(Archive &ar, RCP<const BooleanAtom> &)
724 template <
class Archive>
725 RCP<const Basic> load_basic(Archive &ar, RCP<const And> &)
727 set_boolean container;
729 return make_rcp<const And>(std::move(container));
731 template <
class Archive>
732 RCP<const Basic> load_basic(Archive &ar, RCP<const Or> &)
734 set_boolean container;
736 return make_rcp<const Or>(std::move(container));
738 template <
class Archive>
739 RCP<const Basic> load_basic(Archive &ar, RCP<const Xor> &)
741 vec_boolean container;
743 return make_rcp<const Xor>(std::move(container));
745 template <
class Archive>
746 RCP<const Basic> load_basic(Archive &ar, RCP<const Not> &)
748 RCP<const Boolean> arg;
750 return make_rcp<const Not>(arg);
752 template <
class Archive>
753 RCP<const Basic> load_basic(Archive &ar, RCP<const Piecewise> &)
757 return make_rcp<const Piecewise>(std::move(vec));
759 template <
class Archive>
760 RCP<const Basic> load_basic(Archive &ar, RCP<const Contains> &)
762 RCP<const Basic> expr;
763 RCP<const Set> contains_set;
764 ar(expr, contains_set);
765 return make_rcp<const Contains>(expr, contains_set);
767 template <
class Archive>
768 RCP<const Basic> load_basic(Archive &ar, RCP<const Reals> &)
772 template <
class Archive>
773 RCP<const Basic> load_basic(Archive &ar, RCP<const Rationals> &)
777 template <
class Archive>
778 RCP<const Basic> load_basic(Archive &ar, RCP<const EmptySet> &)
782 template <
class Archive>
783 RCP<const Basic> load_basic(Archive &ar, RCP<const Integers> &)
787 template <
class Archive>
788 RCP<const Basic> load_basic(Archive &ar, RCP<const UniversalSet> &)
792 template <
class Archive>
793 RCP<const Basic> load_basic(Archive &ar, RCP<const Union> &)
797 return make_rcp<const Union>(std::move(union_set));
799 template <
class Archive>
800 RCP<const Basic> load_basic(Archive &ar, RCP<const Complement> &)
802 RCP<const Set> universe, container;
803 ar(universe, container);
804 return make_rcp<const Complement>(universe, container);
806 template <
class Archive>
807 RCP<const Basic> load_basic(Archive &ar, RCP<const ImageSet> &)
809 RCP<const Basic> sym, expr;
812 return make_rcp<const ImageSet>(sym, expr, base);
814 template <
class Archive>
815 RCP<const Basic> load_basic(Archive &ar, RCP<const FiniteSet> &)
819 return make_rcp<const FiniteSet>(set);
821 template <
class Archive>
822 RCP<const Basic> load_basic(Archive &ar, RCP<const ConditionSet> &)
824 RCP<const Basic> sym;
825 RCP<const Boolean> condition;
827 return make_rcp<const ConditionSet>(sym, condition);
829 #ifdef HAVE_SYMENGINE_MPFR
830 template <
class Archive>
831 RCP<const Basic> load_basic(Archive &ar, RCP<const RealMPFR> &)
836 return make_rcp<const RealMPFR>(mpfr_class(num, prec, 10));
839 template <
class Archive>
840 RCP<const Basic> load_basic(Archive &ar, RCP<const Derivative> &)
842 RCP<const Basic> arg;
845 return make_rcp<const Derivative>(arg, std::move(set));
847 template <
class Archive>
848 RCP<const Basic> load_basic(Archive &ar, RCP<const Subs> &)
850 RCP<const Basic> arg;
851 map_basic_basic dict;
853 return make_rcp<const Subs>(arg, std::move(dict));
856 template <
class Archive,
class T>
858 load_basic(Archive &ar, RCP<const T> &,
859 typename std::enable_if<std::is_base_of<OneArgFunction, T>::value,
860 int>::type * =
nullptr)
862 RCP<const Basic> arg;
864 return make_rcp<const T>(arg);
866 template <
class Archive,
class T>
868 load_basic(Archive &ar, RCP<const T> &,
869 typename std::enable_if<std::is_base_of<TwoArgFunction, T>::value,
870 int>::type * =
nullptr)
872 RCP<const Basic> arg1, arg2;
874 return make_rcp<const T>(arg1, arg2);
876 template <
class Archive>
877 RCP<const Basic> load_basic(Archive &ar, RCP<const FunctionSymbol> &)
882 return make_rcp<const FunctionSymbol>(name, std::move(vec));
884 template <
class Archive>
885 RCP<const Basic> load_basic(Archive &ar, RCP<const FunctionWrapper> &)
887 throw SerializationError(StreamFmt()
888 << __FILE__ <<
":" << __LINE__
890 <<
": " << __PRETTY_FUNCTION__
892 <<
"Loading of this type is not implemented.");
894 template <
class Archive,
class T>
896 load_basic(Archive &ar, RCP<const T> &,
897 typename std::enable_if<std::is_base_of<MultiArgFunction, T>::value,
898 int>::type * =
nullptr)
902 return make_rcp<const T>(std::move(args));
904 template <
class Archive,
class T>
906 load_basic(Archive &ar, RCP<const T> &,
907 typename std::enable_if<std::is_base_of<Relational, T>::value,
908 int>::type * =
nullptr)
910 RCP<const Basic> arg1, arg2;
912 return make_rcp<const T>(arg1, arg2);
914 template <
class Archive,
class T>
915 RCP<const Basic> load_basic(
916 Archive &ar, RCP<const T> &,
917 typename std::enable_if<not(std::is_base_of<Relational, T>::value
918 or std::is_base_of<ComplexBase, T>::value
919 or std::is_base_of<OneArgFunction, T>::value
920 or std::is_base_of<MultiArgFunction, T>::value
921 or std::is_base_of<TwoArgFunction, T>::value),
922 int>::type * =
nullptr)
924 throw SerializationError(StreamFmt()
925 << __FILE__ <<
":" << __LINE__
927 <<
": " << __PRETTY_FUNCTION__
929 <<
"Loading of this type is not implemented.");
932 template <
class Archive>
933 inline void save_typeid(Archive &ar, TypeID &t)
937 "TypeID cannot be saved to a 8 bit int.");
941 template <
class Archive>
942 inline void load_typeid(Archive &ar, TypeID &t)
947 throw SerializationError(
"TypeID out of range");
949 t =
static_cast<TypeID
>(i);
953 template <
class Archive,
class T>
959 throw SerializationError(
"Need a RCPBasicAwareInputArchive");
961 ptr = ar_ptr->template load_rcp_basic<T>();
The base class for SymEngine.
static RCP< const Number > from_two_nums(const Number &re, const Number &im)
void rtti()
Overload the rtti function to enable dynamic_cast.
static RCP< const Number > from_two_ints(const Integer &n, const Integer &d)
Main namespace for SymEngine package.
RCP< const Dummy > dummy()
inline version to return Dummy
std::enable_if< std::is_integral< T >::value, RCP< const Integer > >::type integer(T i)
RCP< const Symbol > symbol(const std::string &name)
inline version to return Symbol
RCP< const Number > mulnum(const RCP< const Number > &self, const RCP< const Number > &other)
Multiply self and other
RCP< const Reals > reals()
RCP< const EmptySet > emptyset()
RCP< const Integers > integers()
RCP< const Basic > exp(const RCP< const Basic > &x)
Returns the natural exponential function E**x = pow(E, x)
RCP< const UniversalSet > universalset()
RCP< const Constant > constant(const std::string &name)
inline version to return Constant
void CEREAL_SAVE_FUNCTION_NAME(Archive &ar, RCP< const T > const &ptr)
Saving for SymEngine::RCP.
void CEREAL_LOAD_FUNCTION_NAME(Archive &ar, RCP< const T > &ptr)
Loading for SymEngine::RCP.
RCP< const Rationals > rationals()
RCP< const Number > addnum(const RCP< const Number > &self, const RCP< const Number > &other)
Add self and other