1、实现一个C++ API,用于计算矩形面积的。
新建头文件Rectangle.h
#ifndef RECTANGLE_H #define RECTANGLE_H namespace shapes { class Rectangle { public: int x0, y0, x1, y1; Rectangle(); Rectangle(int x0, int y0, int x1, int y1); ~Rectangle(); int getArea(); void getSize(int* width, int* height); void move(int dx, int dy); }; } #endif新建对应的类类型实现文件Rectangle.cpp
#include "Rectangle.h" namespace shapes { // 默认构造 Rectangle::Rectangle () {} // 有参构造 Rectangle::Rectangle (int x0, int y0, int x1, int y1) { this->x0 = x0; this->y0 = y0; this->x1 = x1; this->y1 = y1; } // 析构函数 Rectangle::~Rectangle () {} // 获取矩形的面积 int Rectangle::getArea () { return (this->x1 - this->x0) * (this->y1 - this->y0); } // 获取矩形的长宽 // Put the size in the pointer args void Rectangle::getSize (int *width, int *height) { (*width) = x1 - x0; (*height) = y1 - y0; } // 移动矩形位置 void Rectangle::move (int dx, int dy) { this->x0 += dx; this->y0 += dy; this->x1 += dx; this->y1 += dy; } }2、在Cython声明上述的成员,Cython将这些声明放在Rectangle.pxd文件,可以将它看着是Cython可读的头文件。
cdef extern from "Rectangle.cpp": pass # Declare the class with cdef cdef extern from "Rectangle.h" namespace "shapes": cdef cppclass Rectangle: Rectangle() except + Rectangle(int, int, int, int) except + int x0, y0, x1, y1 int getArea() void getSize(int* width, int* height) void move(int, int)第1~2两行是显示指明包含C++的代码文件,也可以在这里写,再后续的.pyx文件中通过如下代码指明也可以。
# distutils: sources = Rectangle.cpp
3 最后一步,通过Cython开放Rectangle接口,新建rect.pyx文件
# distutils: language = c++ from Rectangle cimport Rectangle # Create a Cython extension type which holds a C++ instance # as an attribute and create a bunch of forwarding methods # Python extension type. cdef class PyRectangle: cdef Rectangle c_rect # Hold a C++ instance which we're wrapping def __cinit__(self, int x0, int y0, int x1, int y1): self.c_rect = Rectangle(x0, y0, x1, y1) def get_area(self): return self.c_rect.getArea() def get_size(self): cdef int width, height self.c_rect.getSize(&width, &height) return width, height def move(self, dx, dy): self.c_rect.move(dx, dy)第一行的# distutils: language = c++是显示告诉Cython按照C++语言编译。
4 脚本编译setup.py
from distutils.core import setup from Cython.Build import cythonize setup(ext_modules=cythonize("rect.pyx"))编译链接: python3 setup.py build_ext --inplace 生成rect.xxx.so文件
5 接口测试,当前目录下终端python3或ipython3
import rect x0, y0, x1, y1 = 1, 2, 3, 4 rect_obj = rect.PyRectangle(x0, y0, x1, y1) print(dir(rect_obj)) print('矩形长宽: ',rect_obj.get_size()) #矩形长宽: (2, 2) print('矩形面积: ',rect_obj.get_area()) 矩形长宽: (2, 2)总结
展望
函数重载操作符重载模板CPP标准库静态成员方法