假设我有一个包含以下代码的 .h 文件:
class MyClass
{
public:
int Attribute1;
int Attribute2;
MyClass(){};
virtual ~MyClass(){};
virtual void Method1(string var1);
virtual float Method2(float var2);
};
和一个相关的 .pyx 文件:
cdef class PyClass:
cdef MyClass *classptr
[standard __cinit__ and __dealloc__ declarations ]
cdef int Attribute1;
def Method1(self, var1):
self.classptr.Method1(var1)
... 和 pxd 文件:
cdef extern from "mycode.h":
cdef cppclass MyClass:
MyClass() except +
int Attribute1
void Method1(string)
然后我使用 setup.py 创建一个 .so 库以导入 python 模块。
请注意,尽管 MyClass::Method2 和 MyClass::Attribute2 存在于 c++ 中,但我没有在 Cython 中提及它们,因此它们在 .so 库中不可见。也许我这样做是因为它们被 MyClass::Method1() 间接使用,或者只是因为我不打算在 python 代码中调用它们。
这是一种可能导致问题/怪异行为的不良做法吗? 如果是,为什么?
最佳答案
cdef class PyClass:
cdef MyClass *classptr
# ...
cdef int Attribute1;
Attribute1
并不像您想象的那样。它是作为 PyClass
的一部分存储的单独值,与 classptr
中的 Attribute1
无关。您可能想改写一个属性。
但是,要回答您的问题:
是的,您只包装您感兴趣的特定函数就可以了。Cython 不需要知道您的 C++ 类的所有细节——它只需要知道足够的细节来使用它们生成有效的 C++ 代码.省略一些有用的事情的简单示例:
模板。例如
std::string
实际上是一个模板类型定义,但 Cython 包装器可能不一定知道这一点,或者对于可选的分配器模板类型,或者对于 Cython 不知道的数字模板类型真心支持。复杂的继承层次结构:您关心的函数是否实际上来自基类并不重要。只需包装您正在使用的派生类。
返回其他类的接口(interface) - 因为那时您需要包装第二个类(这可能会公开第三个类...)。
除了无法调用您尚未从 python 包装的代码之外,确实没有任何后果。 Cython 的 C++ 支持(并且可能永远)有些不完整,通常需要为其提供简化的 C++ 接口(interface)才能完成任何工作。
关于python - 在 C++/Cython 中,是否可以仅声明相关属性在 Python 中可见?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58842108/