跟进how to pass numpy array to Cython function correctly?的问题:
当将Cython中的numpy.ndarrays传递给只处理连续数组的C函数时,执行之间是否存在差异:
np.ndarray[double, ndim=1, mode="c"] arr = np.ascontiguousarray(np.array([1,2,3],dtype=float))
和
np.ndarray[double, ndim=1, mode="c"] arr = np.asarray(np.array([1,2,3],dtype=float), order="c")
都是必要的吗? np.ascontiguous
是否已经暗示数组将采用可以分配给具有mode=c
声明的数组的格式?
答案 0 :(得分:6)
ascontiguousarray
ascontiguousarray
表示它将返回C有序数组,所以是的,如果您使用c
,则可以假设数据在asarray
中排序模式。
然后回答两者之间的差异,我们可以阅读来源。
return array(a, dtype, copy=False, order=order)
(docs)执行此操作:
ascontiguousarray
return array(a, dtype, copy=False, order='C', ndmin=1)
(link)执行此操作:
order='C'
因此,当您使用ascontiguousarray
调用asarray时,与0
的唯一区别在于您选择了ndmin的默认值,即print asarray(4,dtype='float',order='c').shape
()
print ascontiguousarray(4,dtype='float').shape
(1,)
。当您在单个数字而不是列表上使用这两种方法时,这归结为这种差异:
ascontiguousarray
这取决于你,但我更喜欢atleast1d
,因为我经常依赖于处理数组的shape属性的可能性,并期望它是非空的。从某种意义上说,它就像同时调用{{1}}一样。
答案 1 :(得分:1)
你应该能够做到:
np.ndarray[double, ndim=1, mode="c"] arr = np.array([1,2,3], dtype=np.float64, order="c")
来自np.array
的文档:
order : {'C', 'F', 'A'}, optional
Specify the order of the array. If order is 'C' (default), then the
array will be in C-contiguous order (last-index varies the
fastest). If order is 'F', then the returned array
will be in Fortran-contiguous order (first-index varies the
fastest). If order is 'A', then the returned array may
be in any order (either C-, Fortran-contiguous, or even
discontiguous).
我的理解是,如果您尝试传递的数组是从另一个数组的某个非连续切片生成的,那么您只需要使用np.ascontiguousarray
。如果从头开始创建数组,则不需要。
例如:
a = np.arange(10)
a.flags['C_CONTIGUOUS'] # True
b = a[::2]
b.flags['C_CONTIGUOUS'] # False
c = np.ascontiguousarray(b)
c.flags['C_CONTIGUOUS'] # True
另外,也许可以考虑使用typed memoryview接口
double[::1] arr = np.array([1,2,3], dtype=np.float64)