无法将Python dict实例转换为C++类型,求问题排查
问题:Python字典转C++ std::map时类型转换失败
我尝试将Python的dict[str, object]传递到C中操作,希望在C中保留该对象,但运行时报错:Unable to cast Python instance of type <class 'dict'> to C++。
相关代码
C++代码
typedef std::map<std::string, py::object> dataMap; void init_basicWindowMule(pybind11::module_ & m) { pybind11::class_<testObject, QObject> widgetClass(m, "basicWindow"); widgetClass.def(pybind11::init<>()); widgetClass.def("create", [](py::object obj) { manager = new testObject(); manager->setData(obj.cast<dataMap>()); }); }
Python调用代码
PyBindTest.basicWindow.create({"someStuff":testObject()})
问题原因与解决方法
- 直接用
obj.cast<dataMap>()无法让pybind11自动完成Python字典到std::map<std::string, py::object>的转换,尤其是当字典包含自定义C++对象实例时,这种隐式转换不被支持。 - 正确做法是手动遍历Python字典,逐个处理键值对后存入C++的
std::map,同时提前校验输入类型避免异常。
修改后的C++代码如下:
typedef std::map<std::string, py::object> dataMap; void init_basicWindowMule(pybind11::module_ & m) { pybind11::class_<testObject, QObject> widgetClass(m, "basicWindow"); widgetClass.def(pybind11::init<>()); widgetClass.def("create", [](py::object obj) { // 校验输入是否为Python字典 if (!py::isinstance<py::dict>(obj)) { throw py::type_error("Expected a Python dict"); } py::dict py_dict = obj.cast<py::dict>(); dataMap cpp_map; // 遍历字典转换键值对 for (auto& item : py_dict) { std::string key = py::cast<std::string>(item.first); py::object value = item.second; cpp_map[key] = value; } manager = new testObject(); manager->setData(cpp_map); }); }
说明
手动遍历转换能明确控制每个键值对的处理过程,py::object可以完整保留Python侧的对象引用(包括自定义的testObject实例),满足在C++中保留对象的需求,同时提前的类型校验能避免非法输入导致的异常。
内容的提问来源于stack exchange,提问作者Dariusz
相关产品推荐
相关产品推荐

