ad.hpp
Go to the documentation of this file.
1 /*
2  * Copyright 2021 INRIA
3  */
4 
5 #ifndef __pycppad_ad_hpp__
6 #define __pycppad_ad_hpp__
7 
8 #include "pycppad/fwd.hpp"
9 #include "pycppad/cast.hpp"
10 
11 #include <eigenpy/user-type.hpp>
12 #include <eigenpy/ufunc.hpp>
13 
14 namespace pycppad
15 {
16  namespace bp = boost::python;
17 
18  template<typename _Scalar>
19  class ADVisitor
20  : public bp::def_visitor< ADVisitor<_Scalar> >
21  {
22  public:
23  typedef _Scalar Scalar;
24  typedef ::CppAD::AD<Scalar> AD;
25 
26  template<class PyClass>
27  void visit(PyClass& cl) const
28  {
29  cl
30  .def(bp::init<>(bp::arg("self"),"Default constructor"))
31  .def(bp::init<Scalar>(bp::args("self","value"),
32  std::string("Constructor from a ").append(bp::type_id<Scalar>().name()).c_str()))
33  .def(bp::init<AD>(bp::args("self","other"),"Copy constructor"))
34  .def(bp::self + bp::self)
35  .def(bp::self - bp::self)
36  .def(bp::self * bp::self)
37  .def(bp::self / bp::self)
38  .def(bp::self += bp::self)
39 #ifdef __clang__
40 #pragma GCC diagnostic push
41 #pragma GCC diagnostic ignored "-Wself-assign-overloaded"
42 #endif
43  .def(bp::self /= bp::self)
44  .def(bp::self -= bp::self) // See https://bugs.llvm.org/show_bug.cgi?id=43124 for the bug
45 #ifdef __clang__
46 #pragma GCC diagnostic pop
47 #endif
48  .def(bp::self *= bp::self)
49 
50  .def("abs_me", &AD::abs_me, bp::arg("self"))
51  .def("acos_me", &AD::acos_me, bp::arg("self"))
52  .def("asin_me", &AD::asin_me, bp::arg("self"))
53  .def("atan_me", &AD::atan_me, bp::arg("self"))
54  .def("cos_me", &AD::cos_me, bp::arg("self"))
55  .def("cosh_me", &AD::cosh_me, bp::arg("self"))
56  .def("exp_me", &AD::exp_me, bp::arg("self"))
57  .def("fabs_me", &AD::fabs_me, bp::arg("self"))
58  .def("log_me", &AD::log_me, bp::arg("self"))
59  .def("sin_me", &AD::sin_me, bp::arg("self"))
60  .def("sign_me", &AD::sign_me, bp::arg("self"))
61  .def("sinh_me", &AD::sinh_me, bp::arg("self"))
62  .def("sqrt_me", &AD::sqrt_me, bp::arg("self"))
63  .def("tan_me", &AD::tan_me, bp::arg("self"))
64  .def("tanh_me", &AD::tanh_me, bp::arg("self"))
65  .def("asinh_me", &AD::asinh_me, bp::arg("self"))
66  .def("acosh_me", &AD::acosh_me, bp::arg("self"))
67  .def("atanh_me", &AD::atanh_me, bp::arg("self"))
68  .def("erf_me", &AD::erf_me, bp::args("self","complement"))
69  .def("expm1_me", &AD::expm1_me, bp::arg("self"))
70  .def("log1p_me", &AD::log1p_me, bp::arg("self"))
71 
72  .def("__str__",&print)
73  .def("__repr__",&print)
74 
75  .def("__float__",&::CppAD::Value<Scalar>)
76  .def("__int__",&internal::Cast<AD,int64_t>::run)
77  ;
78  }
79 
80  private:
81 
82  static std::string print(const AD & self)
83  {
84  std::stringstream ss;
85  ss << get_class_name() << "(" << self <<")";
86  return ss.str();
87  }
88 
89  protected:
90 
91  static std::string & get_class_name()
92  {
93  static std::string class_name;
94  return class_name;
95  }
96 
97  static void set_class_name(const std::string & class_name)
98  {
99  get_class_name() = class_name;
100  }
101 
102  public:
103 
104 
105  static void expose(const std::string & class_name = "AD")
106  {
107  set_class_name(class_name);
108  bp::class_<AD>(class_name.c_str(),
109  std::string("AD type corresponding to the scalar type ").append(bp::type_id<Scalar>().name()).c_str(),
110  bp::no_init)
111  .def(ADVisitor<Scalar>());
112 
113  bp::def("Value",&::CppAD::Value<Scalar>,
114  bp::arg("x"),
115  "Conversion from AD to Base type");
116 
117  eigenpy::registerNewType<AD>();
118  eigenpy::registerCommonUfunc<AD>();
119 
120  eigenpy::registerCast<AD,double>(false);
121  eigenpy::registerCast<double,AD>(true);
122  eigenpy::registerCast<AD,float>(false);
123  eigenpy::registerCast<float,AD>(true);
124  eigenpy::registerCast<AD,long>(false);
125  eigenpy::registerCast<long,AD>(true);
126  eigenpy::registerCast<AD,int>(false);
127  eigenpy::registerCast<int,AD>(true);
128  }
129  };
130 }
131 
132 #endif //#ifndef __pycppad_ad_hpp__
Definition: ad.hpp:21
::CppAD::AD< Scalar > AD
Definition: ad.hpp:24
_Scalar Scalar
Definition: ad.hpp:23
static void set_class_name(const std::string &class_name)
Definition: ad.hpp:97
static void expose(const std::string &class_name="AD")
Definition: ad.hpp:105
void visit(PyClass &cl) const
Definition: ad.hpp:27
static std::string & get_class_name()
Definition: ad.hpp:91
Definition: ad.hpp:15
Definition: cast.hpp:19