Python 在cython中使用numpy掩蔽

Python 在cython中使用numpy掩蔽,python,numpy,cython,Python,Numpy,Cython,我正在尝试将一些Python代码转换为Cython,并且在尝试将函数定义为cdef时遇到了一些问题 大多数问题归结为屏蔽不能像Python中那样工作。我想知道这是否是cdef的一个限制(如果我将其保留为def,效果很好),或者我是否可以做些什么 比如这个方法 cdef func(double[:,:,:,:] arg1): mask = arg1 > 0 ... 已失败,出现编译错误: Error compiling Cython file: --------------

我正在尝试将一些Python代码转换为Cython,并且在尝试将函数定义为
cdef
时遇到了一些问题

大多数问题归结为屏蔽不能像Python中那样工作。我想知道这是否是
cdef
的一个限制(如果我将其保留为
def
,效果很好),或者我是否可以做些什么

比如这个方法

cdef func(double[:,:,:,:] arg1):
    mask = arg1 > 0
    ...
已失败,出现编译错误:

Error compiling Cython file:
------------------------------------------------------------ ...
    func (double[:,:,:,:] arg1):
        mask = arg1 > 0
                   ^
------------------------------------------------------------

cythonfile.pyx:43:20: Invalid types for '>' (double[:, :, :, :], long)
所以我会把你的函数签名改为

cdef func(np.ndarray[np.float_t, ndim=4] arg1):
另外,您正在比较
浮点
数组和
长整数
常量。换成

mask = arg1 > 0.

要将
float
float

进行比较,
double[:,:,:,:,:]
符号指定参数将被“解释”为。这些支持很多操作,但不支持向量化比较

但是,很容易将内存视图解释为函数中的NumPy数组:

import numpy as np

cdef func(double[:,:,:,:] arg1):
    arg1arr = np.asarray(arg1)
    mask = arg1arr > 0.
这甚至不需要拷贝,所以在内存视图上执行
np.asarray
基本上是“免费的”。这允许将内存视图的优点与NumPy阵列上可能的矢量化操作结合起来


然而,对于不需要Cython的向量化操作,可以在纯python函数中执行所有向量化操作,并且只使用Cython完成“普通NumPy”函数无法完成的繁重任务。

是否应该定义
cdef funct(np.ndarray[np.float\u t,ndim=4]arg1)
?另外,
0
是一个
长整数
。将其替换为
0。
以获得
浮点值
@NilsWerner:我刚刚尝试并更改了类型,似乎可以。我以前的代码使用了
double[:,:]
,所以从来没有想过,但对于该代码,我没有使用掩蔽。我想有人需要告诉cython,这是一个允许掩蔽的numpy阵列。谢谢我想,
double[:,:]
只允许对元素进行单独寻址,但不允许像您正在做的那样进行矢量化操作。是的,我也这么认为。我以前从未在Cython中使用过向量化操作。传入
np.ndarray
double[…]
参数在性能上有什么区别吗?您说过创建
np.asarray
是“免费的”,但其他操作也是如此吗?@orange这取决于您的用例。这里已经介绍了几个方面,例如,或者在一些博客中。MemoryView的问题在于某些矢量化操作不可用。另一方面,矢量化操作不需要Cython(因为它们与Python一样快)。@orange在高速数学中使用相同的ndarray和[:,:]格式的代码时,我没有看到性能上的差异libraries@Matt:如果转换为
np.ndarray
免费,则有意义。谢谢你的澄清。