Cython:缓冲区类型不匹配,预期 'int' 但得到 'long'

Cython: Buffer type mismatch, expected 'int' but got 'long'

我无法将这个整数的内存视图传递给这个(相当微不足道的)函数。 Python 给我这个错误:

ValueError: Buffer dtype mismatch, expected 'int' but got 'long'

有人可以帮助我了解发生了什么吗?在 Whosebug 周围搜索,它似乎与 python 解释类型的方式以及 C 解释类型的方式有关。

%%cython
def myfunction(int [:] y):
    pass

# Python code
import numpy as np
y = np.array([0, 0, 1, 1])
myfunction(y)

这会产生上面的 ValueError

编辑:这是我发现的其他一些东西。

澄清一下,如果我通过以下方式声明 y,此错误仍然存​​在:

y = np.array([0, 0, 1, 1], dtype='int')
y = np.array([0, 0, 1, 1], dtype=np.int)
y = np.array([0, 0, 1, 1], dtype=np.int64)

但是,如果我用

声明 y,它会起作用
y = np.array([0, 0, 1, 1], dtype=np.int32)

有没有人想给个建议,为什么会这样?投入 np.int32 会在不同的计算机上工作吗? (我使用 macbook pro retina,2013。)

您正在使用 Cython 的 int 类型,它只是 C int。我认为在 Mac(或大多数架构)上它是 int 32 位的。参见 wiki or intel or Does the size of an int depend on the compiler and/or processor?

另一方面,long 表示 int64。 dtype='int'dtype=np.int 都等同于 np.int64.

我认为您可以将其明确定义为 numpy 类型之一:

cimport numpy as np
import numpy as np
cdef myfunction(np.ndarray[np.int64_t, ndim=1] y):
     #do something
     pass

这样读起来更清楚,以后不会混淆。

编辑

较新的 memoryviews 语法是这样的:

cdef myfunction(double[:] y):
    #do something with y
    pass

我按照错误消息告诉我的做了:我将 memoryview 基类型从 int 更改为 long,它似乎有效。

%%cython
def fun(long[:] x):
    return x[0]

y=np.array([1,2,3],dtype=int)
fun(y)    # returns 1

我遇到了同样的问题。受一博回答的启发,我使用了.astype(int),解决了问题。