用Cython优化NumPy

2024-09-27 19:27:23 发布

您现在位置:Python中文网/ 问答频道 /正文

我目前正在尝试优化我用纯Python编写的代码。这段代码在我处理NumPy数组时使用了大量的NumPy。下面您可以看到我转换为Cython的最简单的类。它只做两个Numpy数组的乘法运算。这里:

bendingForces = self.matrixPrefactor * membraneHeight

我的问题是,如果我看到“cython-a”生成的C代码有很多NumPy调用,这看起来不是很有效。在

^{pr2}$

我的想法是使用两个for循环并迭代数组的条目。也许我可以用编译器来优化SIMD操作?!我试过了,我可以编译,但结果很奇怪,而且花了很长时间。下面是替换函数的代码:

cpdef np.ndarray calculate( self, np.ndarray membraneHeight ) :

    cdef index_t index1, index2 # corresponds to: cdef Py_ssize_t index1, index2
    for index1 in range( self.matrixSize ):
        for index2 in range( self.matrixSize ):
            self.bendingForces[ index1, index2 ] = self.matrixPrefactor.data[ index1, index2 ] * membraneHeight.data[ index1, index2 ]
    return self.bendingForces

然而,正如我所说的,这段代码非常慢,并且不能像预期的那样工作。我做错什么了?什么是最好的方法来优化这一点和删除NumPy调用操作?在


Tags: 代码inselfnumpyfornprange数组
2条回答

对于简单的矩阵乘法,NumPy代码已经只在本机进行循环和乘法,所以很难在Cython中击败它。Cython非常适合于将Python中的循环替换为Cython中的循环的情况。代码比NumPy慢的原因之一是,每次在数组中执行索引查找时

self.bendingForces[ index1, index2 ] = self.matrixPrefactor.data[ index1, index2 ] * membraneHeight.data[ index1, index2 ]

它执行更多的计算,比如边界检查(索引是有效的)。如果将索引强制转换为无符号整数,则可以在函数之前使用修饰符@cython.boundscheck(False)。在

有关加速Cython代码的更多详细信息,请参见这个tutorial。在

你可以通过使用

for index1 from 0 <= index1 < max1:

而不是使用一个我不确定是键入的范围。在

你检查过this out和{a2}了吗?在

相关问题 更多 >

    热门问题