Reputation: 858
I have 2 questions, both relating to how arguments between Python and C++ mix... I have a function in C++ which I am calling from python, and my function takes dates and strings.
Is a python str
the same as a C++
class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >
And secondly, my function needs a date of type class boost::gregorian::date
, does anyone know how I can give a date in python that will be read with the correct signature?
Help much appreciated! I hope this is a fairly simple problem, I'm just not very experienced with different types of signatures (which doesn't bode well for my current experimentation into linking Python and C++)!
Upvotes: 1
Views: 780
Reputation: 153909
No. In order to call Python functions from C or C++, you have to use
the Python C API. In the case of a C++ string, this will mean first
converting it to a Python string, using PyString_FromStringAndSize(
cppString.data(), cppString.size() )
, and passing in the resulting
PyObject. And if you want to call an arbitrary function, you'll have to
use PyImport_Import
to load the module, then PyObject_GetAttrString
to get the function (Python functions are attributes, just like
everything else), then use PyObject_CallObject
to call it, after
having converted all of the arguments and put them in a tuple (all via
functions in the Python C API).
Upvotes: 1
Reputation: 18488
Assuming that you are using boost::python
, let me give you an idea of how to proceed in these cases. Rather than letting boost::python
automatically wrap your function, you provide your own wrapping:
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
)
;
}
Of course you need to provide a method that converts a boost::python::object
into a boost::gregorian::date
object. You have to decide how to handle this. For instance, you could assume that the parameter is a sequence of three integers, or you could allow more complex way of passing the parameters, or define a new class that wraps the gregorian date and all of its method and exposes it directly to Python.
As for your first question, when using boost::python
std::string
s are automatically converted to/from Python strings.
Upvotes: 1