快速索引:使用numpy布尔数组和字符串的Cython

3

我正在尝试加快 Python 脚本的速度。我已经对代码进行了分析,并已经在纯 Python 中重新设计了很多东西。看起来我仍然需要花费大量时间来访问一些 numpy 数组,方法看起来像这样:

KeyArray[BoolArray[index]]

其中KeyArray是ndim=2的字符串数组,BoolArray是ndim=1的包含bool值的数组,而索引则为一个int

我正在尝试学习Cython,以了解它有多快。我编写了以下脚本,但它并不起作用:

import numpy as np
cimport numpy as np

def fastindexer(np.ndarray[np.str_t,ndim=1] KeyArray, np.ndarray [np.bool_t,ndim=2] BoolArray, np.int_t DateIndex):
    cdef np.ndarray[np.str_t,ndim=1] FArray = KeyArray[BoolArray[DateIndex]]
    return FArray

我知道numpy数组中不能直接使用str/bool类型。我尝试进行类型转换,但是不理解应该如何编写。

欢迎任何帮助


@Joe 谢谢你的编辑。现在更容易阅读了。 - VincentH
3
就目前而言,将单个高级索引语句移至Cython不会加快速度。因为它已经有效地全部使用了C。不要专注于将事物转移到Cython上,你是否可以重新思考数据结构?你是否可以重构存储数据的方式,使得KeyArray[BoolArray[index]]变成更像是KeyArray[index]的形式? - Joe Kington
1个回答

1

正如@Joe所说,仅将单个索引语句移至Cython并不能提高速度。如果您决定将更多程序移至Cython,则需要解决一些问题。

1)您使用的是def而不是cdef,这限制了您只能使用Python功能。
2)您使用旧的缓冲区语法。请阅读memoryviews
3)对2-D数组进行切片很慢,因为每次都会创建新的memoryview。尽管如此,它仍比Python快得多,但要获得最佳性能,您需要采用不同的方法。

以下是一些起步信息。

cpdef func():
   cdef int i
   cdef bool[:] my_bool_array = np.zeros(10, dtype=bool)
   # I'm not if this next line is correct 
   cdef char[:,:] my_string_array = np.chararray((10, 10))
   cdef char answer

   for i in range(10):
       answer = my_string_array[ my_bool_array[i] ]

2
你会得到“bool”不是类型标识符的错误信息。 - Wang

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接