bind_virtual_factory.cpp
Go to the documentation of this file.
1 #include <eigenpy/eigenpy.hpp>
3 
4 using std::shared_ptr;
5 namespace bp = boost::python;
6 
7 // fwd declaration
8 struct MyVirtualData;
9 
14  virtual ~MyVirtualClass() {}
15 
16  // polymorphic fn taking arg by shared_ptr
17  virtual void doSomethingPtr(shared_ptr<MyVirtualData> const &data) const = 0;
18  // polymorphic fn taking arg by reference
19  virtual void doSomethingRef(MyVirtualData &data) const = 0;
20 
21  virtual shared_ptr<MyVirtualData> createData() const {
22  return std::make_shared<MyVirtualData>(*this);
23  }
24 };
25 
26 struct MyVirtualData {
28  virtual ~MyVirtualData() {} // virtual dtor to mark class as polymorphic
29 };
30 
31 shared_ptr<MyVirtualData> callDoSomethingPtr(const MyVirtualClass &obj) {
32  auto d = obj.createData();
33  printf("Created MyVirtualData with address %p\n", (void *)d.get());
34  obj.doSomethingPtr(d);
35  return d;
36 }
37 
38 shared_ptr<MyVirtualData> callDoSomethingRef(const MyVirtualClass &obj) {
39  auto d = obj.createData();
40  printf("Created MyVirtualData with address %p\n", (void *)d.get());
41  obj.doSomethingRef(*d);
42  return d;
43 }
44 
46  throw std::runtime_error("Called C++ virtual function.");
47 }
48 
50 struct VirtualClassWrapper : MyVirtualClass, bp::wrapper<MyVirtualClass> {
51  void doSomethingPtr(shared_ptr<MyVirtualData> const &data) const override {
52  if (bp::override fo = this->get_override("doSomethingPtr")) {
56  fo(data);
57  return;
58  }
60  }
61 
66  void doSomethingRef(MyVirtualData &data) const override {
67  if (bp::override fo = this->get_override("doSomethingRef")) {
68  fo(boost::ref(data));
69  return;
70  }
72  }
73 
74  shared_ptr<MyVirtualData> createData() const override {
75  if (bp::override fo = this->get_override("createData")) return fo();
76  return default_createData();
77  }
78 
79  shared_ptr<MyVirtualData> default_createData() const {
81  }
82 };
83 
90 struct DataWrapper : MyVirtualData, bp::wrapper<MyVirtualData> {
95 };
96 
99  // try cast to holder
100  return d;
101 }
102 
105 const MyVirtualData &iden_shared(const shared_ptr<MyVirtualData> &d) {
106  // get boost.python's custom deleter
107  // boost.python hides the handle to the original object in there
108  // dter being nonzero indicates shared_ptr was wrapped by Boost.Python
109  auto *dter = std::get_deleter<bp::converter::shared_ptr_deleter>(d);
110  if (dter != 0) printf("> input shared_ptr has a deleter\n");
111  return *d;
112 }
113 
115 shared_ptr<MyVirtualData> copy_shared(const shared_ptr<MyVirtualData> &d) {
116  auto *dter = std::get_deleter<bp::converter::shared_ptr_deleter>(d);
117  if (dter != 0) printf("> input shared_ptr has a deleter\n");
118  return d;
119 }
120 
121 BOOST_PYTHON_MODULE(bind_virtual_factory) {
123  "MyVirtualClass should be polymorphic!");
125  "MyVirtualData should be polymorphic!");
126 
127  bp::class_<VirtualClassWrapper, boost::noncopyable>(
128  "MyVirtualClass", bp::init<>(bp::args("self")))
129  .def("doSomething", bp::pure_virtual(&MyVirtualClass::doSomethingPtr),
130  bp::args("self", "data"))
131  .def("doSomethingRef", bp::pure_virtual(&MyVirtualClass::doSomethingRef),
132  bp::args("self", "data"))
133  .def("createData", &MyVirtualClass::createData,
134  &VirtualClassWrapper::default_createData, bp::args("self"));
135 
136  bp::register_ptr_to_python<shared_ptr<MyVirtualData> >();
140  bp::class_<DataWrapper, boost::noncopyable>("MyVirtualData", bp::no_init)
141  .def(bp::init<MyVirtualClass const &>(bp::args("self", "model")));
142 
143  bp::def("callDoSomethingPtr", callDoSomethingPtr, bp::args("obj"));
144  bp::def("callDoSomethingRef", callDoSomethingRef, bp::args("obj"));
145 
146  bp::def("iden_ref", iden_ref, bp::return_internal_reference<>());
147  bp::def("iden_shared", iden_shared, bp::return_internal_reference<>());
148  bp::def("copy_shared", copy_shared);
149 }
const MyVirtualData & iden_ref(const MyVirtualData &d)
Take and return a const reference.
data
Definition: setup.in.py:48
void throw_virtual_not_implemented_error()
shared_ptr< MyVirtualData > default_createData() const
shared_ptr< MyVirtualData > callDoSomethingPtr(const MyVirtualClass &obj)
shared_ptr< MyVirtualData > callDoSomethingRef(const MyVirtualClass &obj)
const MyVirtualData & iden_shared(const shared_ptr< MyVirtualData > &d)
Eigen::TensorRef< Tensor > ref(Eigen::TensorRef< Tensor > tensor)
Definition: tensor.cpp:55
virtual void doSomethingRef(MyVirtualData &data) const =0
shared_ptr< MyVirtualData > createData() const override
shared_ptr< MyVirtualData > copy_shared(const shared_ptr< MyVirtualData > &d)
Take and return a shared_ptr.
void doSomethingPtr(shared_ptr< MyVirtualData > const &data) const override
void doSomethingRef(MyVirtualData &data) const override
MyVirtualData(MyVirtualClass const &)
virtual shared_ptr< MyVirtualData > createData() const
virtual void doSomethingPtr(shared_ptr< MyVirtualData > const &data) const =0
BOOST_PYTHON_MODULE(bind_virtual_factory)


eigenpy
Author(s): Justin Carpentier, Nicolas Mansard
autogenerated on Fri Jun 2 2023 02:10:26