In the previous section, python uses ctypes to directly call dynamic libraries and uses Python's C language API to encapsulate C functions. This article outlines the boost_python library that is convenient to encapsulate C + + classes for Python.
To install the boost python Library:
sudo aptitude install libboost-python-dev
Example
The following code simply implements a normal function maxab() and a Student class:
#include <iostream> #include <string> int maxab(int a, int b) { return a>b?a:b; } class Student { private: int age; std::string name; public: Student() {} Student(std::string const& _name, int _age) { name=_name; age=_age; } static void myrole() { std::cout << "I'm a student!" << std::endl; } void whoami() { std::cout << "I am " << name << std::endl; } bool operator==(Student const& s) const { return age == s.age; } bool operator!=(Student const& s) const { return age != s.age; } };
Using the boost.python library to encapsulate is also very simple, as shown in the following code:
#include <Python.h> #include <boost/python.hpp> #include <boost/python/suite/indexing/vector_indexing_suite.hpp> #include <vector> #include "student.h" using namespace boost::python; BOOST_PYTHON_MODULE(student) { // This will enable user-defined docstrings and python signatures, // while disabling the C++ signatures scope().attr("__version__") = "1.0.0"; scope().attr("__doc__") = "a demo module to use boost_python."; docstring_options local_docstring_options(true, false, false); def( "maxab", &maxab, "return max of two numbers.\n" ); class_<Student>("Student", "a class of student") .def(init<>()) .def(init<std::string, int>()) // methods for Chinese word segmentation .def( "whoami", &Student::whoami, "method's doc string..." ) .def( "myrole", &Student::myrole, "method's doc string..." ) .staticmethod("myrole"); // Package STL class_<std::vector<Student> >("StudentVec") .def(vector_indexing_suite<std::vector<Student> >()) ; }
The above code still include s the Python.h file. If not, an error will be reported:
wrap_python.hpp:50:23: fatal error: pyconfig.h: No such file or directory
Compile
There are two ways to compile the above code. One is to use g + + directly under the command line:
g++ -I/usr/include/python2.7 -fPIC wrap_student.cpp -lboost_python -shared -o student.so
First, specify the path of Python.h. if it is Python 3, modify it to the corresponding path. When compiling wrap student.cpp, specify the - fPIC parameter, and link (- lboost Chu Python) to generate a dynamic library (- shared). The generated student.so dynamic library can be directly import ed by python
In [1]: import student
In [2]: student.maxab(2, 5)
Out[2]: 5
In [3]: s = student.Student('Tom', 12)
In [4]: s.whoami()
I am Tom
In [5]: s.myrole()
I'm a student!
In addition, the method has always been to write the setup.py script with python's setuptools:
#!/usr/bin/env python from setuptools import setup, Extension setup(name="student", ext_modules=[ Extension("student", ["wrap_student.cpp"], libraries = ["boost_python"]) ])
Then execute the command to compile:
python setup.py build or sudo python setup.py install
Article copyright belongs to Homo erectus