GCC Code Coverage Report


Directory: ./
File: python/quadruped_walkgen/vector-converter.hpp
Date: 2024-12-02 00:24:10
Exec Total Coverage
Lines: 0 11 0.0%
Branches: 0 12 0.0%

Line Branch Exec Source
1 ///////////////////////////////////////////////////////////////////////////////
2 // BSD 3-Clause License
3 //
4 // Copyright (C) 2018-2020, LAAS-CNRS, University of Edinburgh
5 // Copyright note valid unless otherwise stated in individual files.
6 // All rights reserved.
7 ///////////////////////////////////////////////////////////////////////////////
8
9 #ifndef BINDINGS_PYTHON_QUADRUPED_WALKGEN_VECTOR_CONVERTER_HPP_
10 #define BINDINGS_PYTHON_QUADRUPED_WALKGEN_VECTOR_CONVERTER_HPP_
11
12 #include <Eigen/Dense>
13 #include <boost/python/stl_iterator.hpp>
14 #include <boost/python/to_python_converter.hpp>
15 #include <vector>
16
17 namespace quadruped_walkgen {
18 namespace python {
19
20 namespace bp = boost::python;
21
22 /// @note Registers converter from a provided type to the python
23 /// iterable type to the.
24 template <class T, bool NoProxy = true>
25 struct vector_to_list {
26 static PyObject* convert(const std::vector<T>& vec) {
27 typedef typename std::vector<T>::const_iterator const_iter;
28 bp::list* l = new boost::python::list();
29 for (const_iter it = vec.begin(); it != vec.end(); ++it) {
30 if (NoProxy) {
31 l->append(boost::ref(*it));
32 } else {
33 l->append(*it);
34 }
35 }
36 return l->ptr();
37 }
38 static PyTypeObject const* get_pytype() { return &PyList_Type; }
39 };
40
41 /// @brief Type that allows for registration of conversions from
42 /// python iterable types.
43 struct list_to_vector {
44 /// @note Registers converter from a python iterable type to the
45 /// provided type.
46 template <typename Container>
47 list_to_vector& from_python() {
48 boost::python::converter::registry::push_back(
49 &list_to_vector::convertible, &list_to_vector::construct<Container>,
50 boost::python::type_id<Container>());
51
52 // Support chaining.
53 return *this;
54 }
55
56 /// @brief Check if PyObject is iterable.
57 static void* convertible(PyObject* object) {
58 return PyObject_GetIter(object) ? object : NULL;
59 }
60
61 /// @brief Convert iterable PyObject to C++ container type.
62 ///
63 /// Container Concept requirements:
64 ///
65 /// * Container::value_type is CopyConstructable.
66 /// * Container can be constructed and populated with two iterators.
67 /// I.e. Container(begin, end)
68 template <typename Container>
69 static void construct(
70 PyObject* object,
71 boost::python::converter::rvalue_from_python_stage1_data* data) {
72 namespace python = boost::python;
73 // Object is a borrowed reference, so create a handle indicting it is
74 // borrowed for proper reference counting.
75 python::handle<> handle(python::borrowed(object));
76
77 // Obtain a handle to the memory block that the converter has allocated
78 // for the C++ type.
79 typedef python::converter::rvalue_from_python_storage<Container>
80 storage_type;
81 void* storage = reinterpret_cast<storage_type*>(data)->storage.bytes;
82
83 typedef python::stl_input_iterator<typename Container::value_type> iterator;
84
85 // Allocate the C++ type into the converter's memory block, and assign
86 // its handle to the converter's convertible variable. The C++
87 // container is populated by passing the begin and end iterators of
88 // the python object to the container's constructor.
89 new (storage) Container(iterator(python::object(handle)), // begin
90 iterator()); // end
91 data->convertible = storage;
92 }
93 };
94
95 } // namespace python
96 } // namespace quadruped_walkgen
97
98 #endif // BINDINGS_PYTHON_QUADRUPED_WALKGEN_VECTOR_CONVERTER_HPP_
99