生成指向numpy数组的指针的列表

时间:2018-12-06 03:23:47

标签: arrays numpy pointers cython

我正在Cython(0.29)中实现并使用numpy(1.15.1)

cdef double *proj_points[1024]
cdef np.ndarray[double, ndim=2, mode="c"] array_ptr

for i in range(2):
    array_ptr = np.ascontiguousarray(self.projection[i] @ points, dtype=np.float)
    proj_points[i] = &array_ptr[0, 0]

在第1行中,我定义了指针数组(在堆栈上)。在第2行中,我定义了array_ptr,用于将numpy数组转换为C风格的指向numpy数组的指针。

问题:

当我检查proj_points中的指针时,它们都指向最后一个numpy数组(即循环中的第二个)的同一存储元素。

当前(不令人满意的)解决方法

如果我执行相同的硬编码:

cdef np.ndarray[double, ndim=2, mode="c"] array_ptr0 = np.ascontiguousarray(self.projection[0] @ points, dtype=np.float)
self.proj_points[0] = &array_ptr0[0, 0]

cdef np.ndarray[double, ndim=2, mode="c"] array_ptr1 = np.ascontiguousarray(self.projection[1] @ points, dtype=np.float)
self.proj_points[1] = &array_ptr1[0, 0]

所有指针都指向相应的numpy数组的第一个值。对于上面的循环情况,我也希望这样做,因为在运行时可能会有可变数量的指针。我该如何修饰呢?

到目前为止我也尝试过:

  • cdef array_ptr在循环内,但这在Cython中是非法的(cdef仅在第一级是允许的)。
  • 将循环内的部分放入函数中并具有cdef内部函数,但这不起作用

1 个答案:

答案 0 :(得分:0)

指向数组的指针不是Python参考计数方案的一部分,因此它们不会阻止数组被破坏。

因此,一旦array_ptr在每个循环开始时被重新分配,Python就会破坏它原来用来保存的数组。这意味着proj_points的上一个元素现在是指向不再存在的数组的指针,并且如果尝试读取该数组,则得到的结果完全是不确定的。

您需要保留对持有指针的任何numpy数组的Python引用。