如何以有效的方式将阵列旋转±180°?

Aur*_*rre 0 python optimization

对于C语言和衍生物(Python,Cython,纯C),使用最少的内存和操作将非方形M×N阵列围绕其中心旋转180°的最佳算法是什么?

TaQ*_*gTu 9

现在回答这个问题相对较晚,但总比什么都不做要好。

对于形状为 的 2D numpy 数组H x W

rotated_array = old_array[::-1,::-1] #rotate the array 180 degrees
Run Code Online (Sandbox Code Playgroud)

对于形状为 2D numpy 图像H x W x 3

rotated_image = image[::-1,::-1] #rotate the image 180 degrees
Run Code Online (Sandbox Code Playgroud)


Aur*_*rre 5

假设out是一个初始化拷贝array,MN它们的行和列号,并且我们使用一个语言索引阵列从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]
Run Code Online (Sandbox Code Playgroud)

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]
Run Code Online (Sandbox Code Playgroud)

在4000×3000阵列上需要5.45秒.

相比之下,numpy np.rot90(array, 2)需要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]])
Run Code Online (Sandbox Code Playgroud)

所以这确实是180°旋转.

np.flip(a, 0)

out = array([[7, 8, 9],
             [4, 5, 6],
             [1, 2, 3]])
Run Code Online (Sandbox Code Playgroud)

沿着最后一行是对称的,而不是旋转.

np.flip(np.flip(a, 1), 0)

out = array([[9, 8, 7],
             [6, 5, 4],
             [3, 2, 1]])
Run Code Online (Sandbox Code Playgroud)

也是180°旋转.

所以,是的,谢谢你,我的代码做了它所说的.