将多个C 类包装成一个Python类
Wrapping multiple C++ classes into one Python class
cython允许通过包装其功能和类来使用C和C 库。我想使用的两个库是SFML和Box2D。他们定义了单独的vector2类。是否可以为这两个库编写一个Vector2 Python包装器(以及更多(?我的目标是在与不同库交互时具有单python类型的vector2。
有人已经做了类似的事情吗?这将简化事物并统一我的Python API。我已经包裹了SFML的一部分,但除此之外,我是Cython的新手。
对于参考SFML的vector2看起来像这样:
template <typename T> class Vector2 {
public:
T x;
T y;
Vector2();
Vector2(T X, T Y);
template <typename U> explicit Vector2(const Vector2<U>& vector);
...
};
和box2d向量:
struct b2Vec2 {
float32 x, y;
b2Vec2() {}
b2Vec2(float32 xIn, float32 yIn);
...
};
概述
一般想法是三个步骤:
- 为您的类型写声明
- 用相同的接口单独包装每个类
- 写一个广义矢量包装器
声明
首先,您需要包装类型的Cython声明。一个示例(非常最小(如下。
# This is the Cython interface for Vector2
cdef float float32
cdef extern from "Vector2.hpp" nogil:
# if this was an stl vector, use vector[T, ALLOCATOR=*]
# you must list every template type, even one with default values
cdef cppclass Vector2[T]:
ctypedef T value_type
# Add all the overloads, for example, multiplication
Vector2[T, ALLOCATOR] operator*(const T&) const;
cdef extern from "b2Math.h" nogil:
cdef cppclass b2Vec2:
# Add all overloads, for example, multiplication
void operator*=(float)
接口
接下来,您需要将它们包装成Python包装器。您需要确保它们具有相同的接口,因此可以像另一个一样使用。Python数据模型是您的朋友。一个非常简单的例子是:
cdef class SfmlVector2_32:
# This is a definition for a float32 vector from Sfml
Vector2[float32] c
def __mul__(self, float32 x):
# multiple and assign
B2Vector2_32 copy;
copy.c = c * x
return copy;
cdef class B2Vector2_32:
# This is a definition for a float32 vector from box2
b2Vec2 c
def __mul__(self, float32 x):
# multiple and assign
B2Vector2_32 copy;
copy.c = c;
copy.c *= x
return copy
广义向量
最后,您需要一个简单的包装类,该类绑定了许多向量类型之一,并在类上执行正确的操作。由于Python不是静态键入的,并且由于您包装的每个向量的接口都是相同的,因此很容易:只需在__init__
中初始化正确的向量。
class Vector2_32:
def __init__(self, framework = 'SFML'):
# ideally, perform a dictionary lookup if you have many classes
# O(1) for dict, if/then is O(n)
if framework == 'SFML':
self.vector = SfmlVector2_32()
elif framework == 'BOX2':
self.vector = B2Vector2_32()
else:
raise TypeError("Unrecognized framework.")
def __mul__(self, float32 x):
Vector2_32 copy
copy.vector = vector * x
return copy
思想
这是一个非常糟糕的示例,因为通常您以__imul__
(现场乘法(来实现__mul__
(乘法(,但是它可以贯穿一般的想法。此代码可能有错别字,我现在无法访问机器来立即进行编译。
相关文章:
- 如何在C++中使用pybind11加载一个pickle python列表
- 如果C++对象的类在另一个boost模块中声明,如何使用boost将指向该对象的指针返回到python
- 我想通过带有C++和Python的插件创建一个可扩展的应用程序
- 有没有一个 c++ gmp 库函数与 python gmpy2 库 divm(..) 函数相同?
- 创建一个函数的 Python 绑定,返回指向带有 boost 的向量的指针
- 如何构建一个 setup.py 来编译C++使用 Python、pybind11 和 Mingw-w64 的扩展?
- 在 c++ 中创建一个类似 python 的列表
- 如何将 c++ 类包装到 python 中,以便我可以使用 pybind11 访问其成员的公共方法(成员是一个对象指针)
- 如何制作一个满足SWIG中接口的python类
- 在使用PyInstaller冻结Python脚本时包含一个C++可执行文件
- 加快一个长python代码的速度,因为只有一个块,所以速度很慢
- 如何创建一个接口,允许我访问C++中的按钮(和其他ui)函数,该函数是使用python中的MFC实现的
- OpenCV - 打开一个从C++到Python的XML文件
- 将多个C 类包装成一个Python类
- 调用一个 Python 函数,其中包含来自 boost Python 的可变数量的输入参数
- 包装一个使用char**[in/out]的C函数调用,以在cython中返回一个python列表
- 从C++库创建一个Python包
- redhawksdr导出一个Python脚本和一个c++组件
- 用c++创建一个python对象并调用它的方法
- 是否有可能完全扁平化一个python包,完全删除目录