20struct EIGENPY_DLLAPI Register {
21 static PyArray_Descr *getPyArrayDescr(PyTypeObject *py_type_ptr);
23 static PyArray_Descr *getPyArrayDescrFromTypeNum(
const int type_num);
25 template <
typename Scalar>
26 static PyArray_Descr *getPyArrayDescrFromScalarType() {
27 if (!isNumpyNativeType<Scalar>()) {
28 const std::type_info &info =
typeid(Scalar);
29 if (instance().type_to_py_type_bindings.find(&info) !=
30 instance().type_to_py_type_bindings.end()) {
31 PyTypeObject *py_type = instance().type_to_py_type_bindings[&info];
32 return instance().py_array_descr_bindings[py_type];
36 PyArray_Descr *new_descr =
37 call_PyArray_DescrFromType(NumpyEquivalentType<Scalar>::type_code);
42 template <
typename Scalar>
43 static bool isRegistered() {
44 return isRegistered(Register::getPyType<Scalar>());
47 static bool isRegistered(PyTypeObject *py_type_ptr);
49 static int getTypeCode(PyTypeObject *py_type_ptr);
51 template <
typename Scalar>
52 static PyTypeObject *getPyType() {
53 if (!isNumpyNativeType<Scalar>()) {
54 const PyTypeObject *const_py_type_ptr =
55 bp::converter::registered_pytype<Scalar>::get_pytype();
56 if (const_py_type_ptr == NULL) {
58 ss <<
"The type " <<
typeid(Scalar).name()
59 <<
" does not have a registered converter inside Boot.Python." 61 throw std::invalid_argument(ss.str());
63 PyTypeObject *py_type_ptr =
const_cast<PyTypeObject *
>(const_py_type_ptr);
66 PyArray_Descr *new_descr =
67 call_PyArray_DescrFromType(NumpyEquivalentType<Scalar>::type_code);
68 return new_descr->typeobj;
72 template <
typename Scalar>
73 static PyArray_Descr *getPyArrayDescr() {
74 if (!isNumpyNativeType<Scalar>()) {
75 return getPyArrayDescr(getPyType<Scalar>());
77 return call_PyArray_DescrFromType(NumpyEquivalentType<Scalar>::type_code);
81 template <
typename Scalar>
82 static int getTypeCode() {
83 if (isNumpyNativeType<Scalar>())
84 return NumpyEquivalentType<Scalar>::type_code;
86 const std::type_info &info =
typeid(Scalar);
87 if (instance().type_to_py_type_bindings.find(&info) !=
88 instance().type_to_py_type_bindings.end()) {
89 PyTypeObject *py_type = instance().type_to_py_type_bindings[&info];
90 int code = instance().py_array_code_bindings[py_type];
98 static int registerNewType(
99 PyTypeObject *py_type_ptr,
const std::type_info *type_info_ptr,
100 const int type_size,
const int alignment, PyArray_GetItemFunc *getitem,
101 PyArray_SetItemFunc *setitem, PyArray_NonzeroFunc *nonzero,
102 PyArray_CopySwapFunc *copyswap, PyArray_CopySwapNFunc *copyswapn,
103 PyArray_DotFunc *dotfunc, PyArray_FillFunc *fill,
104 PyArray_FillWithScalarFunc *fillwithscalar);
106 static Register &instance();
111 struct Compare_PyTypeObject {
112 bool operator()(
const PyTypeObject *a,
const PyTypeObject *b)
const {
113 return std::string(a->tp_name) < std::string(b->tp_name);
117 struct Compare_TypeInfo {
118 bool operator()(
const std::type_info *a,
const std::type_info *b)
const {
119 return std::string(a->name()) < std::string(b->name());
123 typedef std::map<const std::type_info *, PyTypeObject *, Compare_TypeInfo>
125 MapInfo type_to_py_type_bindings;
127 typedef std::map<PyTypeObject *, PyArray_Descr *, Compare_PyTypeObject>
129 MapDescr py_array_descr_bindings;
131 typedef std::map<PyTypeObject *, int, Compare_PyTypeObject> MapCode;
132 MapCode py_array_code_bindings;