Pybind11:如何在C++中访问Python对象的property属性?
Pybind11访问Python property属性报错及setter调用方法
问题1:TypeError: 'str' object is not callable的解决
当Python类用@property装饰attr后,attr就变成了属性而非方法——在Python里直接通过obj.attr就能拿到值,不需要加括号调用。但你当前的C++代码里,obj.attr("attr")()是把获取到的字符串结果当成函数去调用,自然会触发"str不可调用"的错误。
修改后的C++代码:
#include <pybind11/pybind11.h> void print_attr(const py::object &obj) { // 直接获取属性值,无需加()调用 std::string attr_value = py::cast<std::string>(obj.attr("attr")); std::cout << attr_value << std::endl; } PYBIND11_MODULE(example, m) { m.def("print_attr", &print_attr); }
如果不需要转成C++字符串,直接输出也可以简化成:
std::cout << py::str(obj.attr("attr")) << std::endl;
问题2:在C++绑定代码中调用attr.setter方法
要调用property的setter,直接给属性赋值即可,Pybind11会自动触发对应的setter逻辑,有两种实现方式:
方式1:直接通过attr赋值
#include <pybind11/pybind11.h> void print_attr(const py::object &obj) { std::string attr_value = py::cast<std::string>(obj.attr("attr")); std::cout << attr_value << std::endl; } void set_attr(py::object &obj, const std::string &value) { // 直接赋值,自动调用@attr.setter obj.attr("attr") = value; } PYBIND11_MODULE(example, m) { m.def("print_attr", &print_attr); m.def("set_attr", &set_attr); }
方式2:使用py::setattr工具函数
也可以用Pybind11提供的py::setattr函数实现同样效果:
void set_attr(py::object &obj, const std::string &value) { py::setattr(obj, "attr", value); }
测试时Python代码可以这样写:
import example obj = Example() example.print_attr(obj) # 输出hello world example.set_attr(obj, "new value") example.print_attr(obj) # 输出new value
内容的提问来源于stack exchange,提问作者Yulong Ao
相关产品推荐
相关产品推荐

