Python参数类型C++签名
我有两个问题,都是关于Python和C++之间参数如何混合的……我在C++中有一个函数,我是从Python调用它的,这个函数需要日期和字符串。
Python中的str
和C++中的
class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >
是一样的吗?
其次,我的函数需要一个类型为class boost::gregorian::date
的日期,有人知道我该如何在Python中提供一个日期,以便它能被正确识别吗?
非常感谢你的帮助!我希望这个问题比较简单,我只是对不同类型的参数签名不太熟悉(这对我目前尝试将Python和C++连接起来的实验来说可不太妙)!
2 个回答
不可以。要从C或C++调用Python函数,你需要使用Python的C接口。对于C++字符串来说,首先要把它转换成Python字符串,可以用PyString_FromStringAndSize(cppString.data(), cppString.size())
这个函数,然后把得到的结果作为PyObject传进去。如果你想调用一个任意的函数,你需要先用PyImport_Import
来加载模块,然后用PyObject_GetAttrString
来获取这个函数(Python函数就像其他东西一样,是属性),最后用PyObject_CallObject
来调用它。在这个过程中,你还需要把所有的参数转换成元组(这些都是通过Python C接口中的函数来完成的)。
假设你在使用 boost::python
,我给你讲讲在这种情况下该怎么做。与其让 boost::python
自动处理你的函数,不如自己来写一个包装函数:
namespace {
void Foo_methodUsingDate( Foo* pointer, const object& dateObject )
{
boost::gregorian::date date = convertFromPython( dateObject );
pointer->methodUsingDate( date );
}
}
void wrap_Foo()
{
class_< Foo >( "Foo" )
.def( "bar",
& Foo::bar
)
.def( "foobar",
& Foo::foobar
)
.def( "methodUsingDate",
& Foo_methodUsingDate
)
;
}
当然,你需要提供一个方法,把 boost::python::object
转换成 boost::gregorian::date
对象。你得决定怎么处理这个转换。比如,你可以假设这个参数是三个整数的序列,或者你可以允许更复杂的参数传递方式,或者定义一个新类,把公历日期和它的所有方法封装起来,直接暴露给 Python。
至于你的第一个问题,当使用 boost::python
时,std::string
会自动转换为 Python 字符串,反之亦然。