免責聲明:是的,我知道約boost::python::map_indexing_suite
。如何包裝一個C++類與構造函數一個std ::地圖或std :: vector的說法並帶有Boost.Python?
任務:我有一個C++類,我想用Boost.Python包裝。它的構造函數需要一個std::map
參數。下面是C++頭:
// myclass.hh
typedef std::map<int, float> mymap_t;
class MyClass {
public:
explicit MyClass(const mymap_t& m);
// ...
};
// ...
這裏是Boost.Python的包裝物(僅主要部分):
// myclasswrapper.cc
#include "mymap.hh"
#include "boost/python.hpp"
#include "boost/python/suite/indexing/map_indexing_suite.hpp"
namespace bpy = boost::python;
// wrapping mymap_t
bpy::class_<mymap_t>("MyMap")
.def(bpy::map_indexing_suite<mymap_t>())
;
// wrapping MyClass
bpy::class_<MyClass>("MyClass", "My example class",
bpy::init<mymap_t>() // ??? what to put here?
)
// .def(...method wrappers...)
;
這將編譯。但是,我不能從Python端創建映射MyClass
對象,因爲我不知道該怎麼傳遞作爲參數傳遞給構造。字典沒有被轉換到自動std::map
-s:
# python test
myclass = MyClass({1:3.14, 5:42.03})
解釋抱怨(這是正確的):
Boost.Python.ArgumentError: Python argument types in
MyClass.__init__(MyClass, dict)
did not match C++ signature:
__init__(_object*, std::__1::map<int, float, ...
和MyMap
在Python端不能與字典或者初始化。
已經用Google搜索了好幾天,最精彩的部分,我能找到的唯一採取的是映射與.def(...)
std::map
參數「正常」的方法的例子。並且在.def(...)
中,您不必明確指定映射方法的參數,它們被神奇地發現。使用構造函數,您必須使用boost::python::init<...>()
,或者至少這是我從文檔中理解的。
問題:
- 要我補充一下到
MyMap
包裝,以幫助map_indexing_suite
轉換從Python字典? - 我應當用
MyClass
包裝在boost::python::init<...>
不同的模板參數? - 任何其他的想法...?
注意:我也看到this accepted answer at SO,然後我向下滾動和讀取@YvesgereY評論:
「爲了記錄在案,map_indexing_suite解決方案不起作用,因爲沒有 隱「dict-> std :: map」from_python轉換器將被應用。「
,我失去了信心:-)
做一個獨立的函數,它將構造'boost :: python :: dict'對象。見[這個答案](http://stackoverflow.com/a/18793953/3962537)的靈感。 –
@DanMašek:非常感謝,您的評論非常有用,它指向了轉換器。我現在回答我自己的問題,見下文。 –