cython:如何创建一个cdef类数组

时间:2015-11-22 03:37:03

标签: cython

我想要一个cdef类的cython数组:

cdef class Child:
    cdef int i

    def do(self):
        self.i += 1

cdef class Mother:
    cdef Child[:] array_of_child

    def __init__(self):
        for i in range(100):
            self.array_of_child[i] = Child()

1 个答案:

答案 0 :(得分:11)

答案是否定的:不可能:newsgroup post of essentially the same question

基本上,数组必须是指向Child的指针数组,而不是Child的直接数组。它几乎必须是这样的,因为在其他地方得到了数组中Child的引用,Child必须保持活着(但不是整个数组),这不会是是否可以确保它们都分配在同一块内存中。另外,如果要调整数组的大小(如果这是一个要求)那么它将使对数组中对象的任何其他引用无效。

有一些明智的工作:

  1. 新闻组帖子中建议的workround就是使用python列表。您还可以使用带有dtype=object的numpy数组。如果您需要在类中访问cdef函数,可以先进行强制转换:

    cdef Child c = <Child?>a[0] # omit the ? if you don't want
                                # the overhead of checking the type.
    c.some_cdef_function()
    

    在内部,这两个选项都存储为PyObject指针的Child指针的C数组,所以效率不如你想象的那么低。

  2. 另一种可能性是将数据存储为C结构(cdef struct ChildStruct: ....),可以很容易地存储为数组。当你需要一个到该结构的Python接口时,你可以定义Child,因此它包含ChildStruct的副本(但是修改不会传播回原始数组),或指向{ {1}}(但是你必须小心确保没有释放指向它的ChildStruct存活的内存。)

  3. 您可以使用Numpy structured array - 这与使用C块结构非常类似,除了Numpy处理内存,并提供Python接口。