对于C语言和衍生物(Python,Cython,纯C),使用最少的内存和操作将非方形M×N阵列围绕其中心旋转180°的最佳算法是什么?
答案 0 :(得分:5)
假设out
是array
,M
和N
的行和列编号的初始化副本,我们使用的语言索引数组从0到(M -1)和(N-1):
在Python中:
def rotate_180(array, M, N, out):
for i in range(M):
for j in range(N):
out[i, N-1-j] = array[M-1-i, j]
4000×3000阵列需要5.82秒。
使用Memviews进行并行化的Cython + OpenMP:
cdef void rotate_180(float[:, :] array, int M, int N, float[:, :] out) nogil:
cdef size_t i, j
with parallel(num_threads=8):
for i in prange(M):
for j in range(N):
out[i, N-1-j] = array[M-1-i, j]
4000×3000阵列需要5.45秒。
相比之下,np.rot90(array, 2)
的numpy需要8.58μs。
编辑:为了避免知道所有评论,这就是它的作用:
a = array([[1, 2, 3],
[4, 5, 6],
[7, 8, 9]])
rotate_180(a, 3, 3, b)
b = array([[9, 8, 7],
[6, 5, 4],
[3, 2, 1]])
np.rot90(a, 2)
out = array([[9, 8, 7],
[6, 5, 4],
[3, 2, 1]])
所以这确实是180°旋转。
np.flip(a, 0)
out = array([[7, 8, 9],
[4, 5, 6],
[1, 2, 3]])
是沿最后一行的对称,而不是旋转。
np.flip(np.flip(a, 1), 0)
out = array([[9, 8, 7],
[6, 5, 4],
[3, 2, 1]])
也是180°旋转。
所以,是的,谢谢你,我的代码按照它说的做了。