是什么导致Python';在嵌入Boost.Python时,s_u main__;u将消失 我将Python嵌入到C++应用程序中。我想在主模块中定义一个函数V,它接受一个字符串并返回一个类a的实例
问题是是什么导致Python';在嵌入Boost.Python时,s_u main__;u将消失 我将Python嵌入到C++应用程序中。我想在主模块中定义一个函数V,它接受一个字符串并返回一个类a的实例,c++,boost-python,C++,Boost Python,问题是A需要嵌入Python的类实例中的一些可用数据,在示例中作为\u env传递-因此我认为可以使用def(…)在方法中定义V,使用lambda捕获所需的数据 但是,当我这样做时,当我尝试获取主模块的字典时,我最终得到了AttributeError:“NoneType”对象没有属性“\uuu dict\uuu” 不需要调用boost的def(…),我就可以获取并添加到主模块中 是否有我做错的事情导致\uuuu main\uuu丢失,并在我尝试访问它时生成一个None?关于如何实现这一点,还有什
A
需要嵌入Python的类实例中的一些可用数据,在示例中作为\u env
传递-因此我认为可以使用def(…)在方法中定义V
,使用lambda捕获所需的数据
但是,当我这样做时,当我尝试获取主模块的字典时,我最终得到了AttributeError:“NoneType”对象没有属性“\uuu dict\uuu”
不需要调用boost的def(…),我就可以获取并添加到主模块中
是否有我做错的事情导致\uuuu main\uuu
丢失,并在我尝试访问它时生成一个None?关于如何实现这一点,还有什么建议吗
void B::processRequest(Ptr<protocol::Message> msg, const std::function<void(const std::string &)> &send) {
try {
//make my_module module available to python
PyImport_AppendInittab("my_module", &initmy_module);
//
Py_Initialize();
//get the main module
py::object main_module((py::handle<>(py::borrowed(PyImport_AddModule("__main__")))));
py::object main_namespace = main_module.attr("__dict__");
py::object my_moduleNamespace((py::handle<>(PyImport_ImportModule("my_module"))));
//add the module to the main namespace
main_namespace["my_module"] = my_moduleNamespace;
//add attribute to namespace
// main_namespace["V"] = py::ptr(this);
auto AFn([this](std::string label) { return ptr<A>(_env, label); });
typedef boost::mpl::vector<Ptr<A>, std::string> AFnSig;
const auto policies = py::default_call_policies();
py::def("V", boost::python::make_function(AFn, policies, AFnSig()));
py::handle<> ignored((PyRun_String((*msg->action).c_str(), Py_file_input, main_namespace.ptr(), main_namespace.ptr())));
} catch (py::error_already_set) {
PyErr_Print();
}
Py_Finalize();
}
void B::processRequest(Ptr msg,const std::function&send){
试一试{
//使my_模块可用于python
PyImport_AppendInittab(“my_模块”&初始化my_模块);
//
Py_初始化();
//获取主模块
py::object main_module((py::handle(py::followed(PyImport_AddModule)(“_umain_uuuuuuuu”;”));
py::object main_namespace=main_module.attr(“u dict_u”);
py::object my_moduleNamespace((py::handle(PyImport_ImportModule(“my_module”)));
//将模块添加到主命名空间
main_名称空间[“我的模块”]=我的模块名称空间;
//将属性添加到命名空间
//main_名称空间[“V”]=py::ptr(this);
自动AFn([this](std::string label){return ptr(_env,label);});
typedef boost::mpl::vector AFnSig;
const auto policies=py::default_call_policies();
py::def(“V”,boost::python::make_函数(AFn,policies,AFnSig());
py::handle被忽略((PyRun_字符串((*msg->action).c_str(),py_文件_输入,main_namespace.ptr(),main_namespace.ptr()));
}捕获(py::错误\u已设置){
PyErr_Print();
}
Py_Finalize();
}
我唯一能想到的解决方法就是使B
callable定义操作符(std::stirng)
但这不起作用,因为我还有另外两个函数需要\u env
,其中一个函数的签名与V
相同,所以就我所见,无法区分调用
编辑:
更改了标题,试图使我所指的内容更清楚。似乎找不到一种方法来处理bp。因此,我提出了使用普通python在名称空间中定义我想要的函数,并注册python函数使用的环境对象。所以,在我能创建的C++ API周围写一个Python包装。
BOOST_PYTHON_MODULE (my_module) {
//env is now exposed to the user but can't be constructed and none of its methods are exposed so it's not so bad. Just the symbol exists.
py::class_<Ptr<Environment>>("Environment", py::no_init);
py::class_<A>("A", py::init<const Ptr<Environment>, std::string>());
}
void B::processRequest(Ptr<protocol::Message> msg, const std::function<void(const std::string &)> &send) {
try {
//make my_module module available to python
PyImport_AppendInittab("my_module", &initmy_module);
//
Py_Initialize();
//get the main module
py::object main_module((py::handle<>(py::borrowed(PyImport_AddModule("__main__")))));
py::object main_namespace = main_module.attr("__dict__");
py::object my_moduleNamespace((py::handle<>(PyImport_ImportModule("my_module"))));
//add the module to the main namespace
main_namespace["my_module"] = my_moduleNamespace;
my_moduleNamespace.attr("environment") = _env;
//HERE - provide the API I want using a native Python function
py::handle<> envRun((PyRun_String("def V(label):\n return my_module.A(my_module.environment,label)", Py_file_input, main_namespace.ptr(), main_namespace.ptr())));
py::handle<> ignored((PyRun_String((*msg->action).c_str(), Py_file_input, main_namespace.ptr(), main_namespace.ptr())));
} catch (py::error_already_set) {
PyErr_Print();
}
Py_Finalize();
}
BOOST_PYTHON_模块(my_模块){
//env现在向用户公开,但无法构造,并且它的任何方法都没有公开,所以它不是那么糟糕。只是符号存在。
py::class_u(“环境”,py::no_init);
py::class_uz(“A”,py::init());
}
void B::processRequest(Ptr msg,const std::function&send){
试一试{
//使my_模块可用于python
PyImport_AppendInittab(“my_模块”&初始化my_模块);
//
Py_初始化();
//获取主模块
py::object main_module((py::handle(py::followed(PyImport_AddModule)(“_umain_uuuuuuuu”;”));
py::object main_namespace=main_module.attr(“u dict_u”);
py::object my_moduleNamespace((py::handle(PyImport_ImportModule(“my_module”)));
//将模块添加到主命名空间
main_名称空间[“我的模块”]=我的模块名称空间;
我的模块空间属性(“环境”)=\u环境;
//这里-使用本机Python函数提供我想要的API
py::handle envRun((PyRun_字符串(“def V(标签):\n返回my_module.A(my_module.environment,label)”,py_文件输入,main_namespace.ptr(),main_namespace.ptr());
py::handle被忽略((PyRun_字符串((*msg->action).c_str(),py_文件_输入,main_namespace.ptr(),main_namespace.ptr()));
}捕获(py::错误\u已设置){
PyErr_Print();
}
Py_Finalize();
}
似乎找不到一种方法来处理bp。因此,我提出了使用普通python在名称空间中定义我想要的函数,并注册python函数使用的环境对象。所以,在我能创建的C++ API周围写一个Python包装。
BOOST_PYTHON_MODULE (my_module) {
//env is now exposed to the user but can't be constructed and none of its methods are exposed so it's not so bad. Just the symbol exists.
py::class_<Ptr<Environment>>("Environment", py::no_init);
py::class_<A>("A", py::init<const Ptr<Environment>, std::string>());
}
void B::processRequest(Ptr<protocol::Message> msg, const std::function<void(const std::string &)> &send) {
try {
//make my_module module available to python
PyImport_AppendInittab("my_module", &initmy_module);
//
Py_Initialize();
//get the main module
py::object main_module((py::handle<>(py::borrowed(PyImport_AddModule("__main__")))));
py::object main_namespace = main_module.attr("__dict__");
py::object my_moduleNamespace((py::handle<>(PyImport_ImportModule("my_module"))));
//add the module to the main namespace
main_namespace["my_module"] = my_moduleNamespace;
my_moduleNamespace.attr("environment") = _env;
//HERE - provide the API I want using a native Python function
py::handle<> envRun((PyRun_String("def V(label):\n return my_module.A(my_module.environment,label)", Py_file_input, main_namespace.ptr(), main_namespace.ptr())));
py::handle<> ignored((PyRun_String((*msg->action).c_str(), Py_file_input, main_namespace.ptr(), main_namespace.ptr())));
} catch (py::error_already_set) {
PyErr_Print();
}
Py_Finalize();
}
BOOST_PYTHON_模块(my_模块){
//env现在向用户公开,但无法构造,并且它的任何方法都没有公开,所以它不是那么糟糕。只是符号存在。
py::class_u(“环境”,py::no_init);
py::class_uz(“A”,py::init());
}
void B::processRequest(Ptr msg,const std::function&send){
试一试{
//使my_模块可用于python
PyImport_AppendInittab(“my_模块”&初始化my_模块);
//
Py_初始化();
//获取主模块
py::object main_module((py::handle(py::followed(PyImport_AddModule)(“_umain_uuuuuuuu”;”));
py::object main_namespace=main_module.attr(“u dict_u”);
py::object my_moduleNamespace((py::handle(PyImport_ImportModule(“my_module”)));
//将模块添加到主命名空间
main_名称空间[“我的模块”]=我的模块名称空间;
我的模块空间属性(“环境”)=\u环境;
//这里-使用本机Python函数提供我想要的API
py::handle envRun((PyRun_字符串(“def V(标签):\n返回my_module.A(my_module.environment,label)”,py_文件输入,main_namespace.ptr(),main_namespace.ptr());
py::handle被忽略((PyRun_字符串((*msg->action).c_str(),py_文件_输入,main_namespace.ptr(),main_namespace.ptr()));
}捕获(py::错误\u已设置){
PyErr_Print();
}
Py_Finalize();
}
问题不在于\uuuuu main\uuuu