Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/338.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python:沿垂直轴镜像图像的最有效方法_Python_Image_Numpy_Opencv - Fatal编程技术网

Python:沿垂直轴镜像图像的最有效方法

Python:沿垂直轴镜像图像的最有效方法,python,image,numpy,opencv,Python,Image,Numpy,Opencv,我有很多图像需要(动态地)翻转,因此我正在寻找使用Python实现这一点的最快方法 最有效的方法是什么 我在磁盘上有图像文件,并尝试了一些方法,如下面我自己的答案所示,但这些方法都是从Numpy阵列开始的,因此可能不是最优的。有更好的方法吗?这里有两种方法,使用: OpenCVcv2.flip() Numpynp.fliplr() 导入包 import cv2 import numpy as np 我有一个numpy阵列中的三个图像,每个图像的分辨率如下所示: images.shape (3,

我有很多图像需要(动态地)翻转,因此我正在寻找使用Python实现这一点的最快方法

最有效的方法是什么


我在磁盘上有图像文件,并尝试了一些方法,如下面我自己的答案所示,但这些方法都是从Numpy阵列开始的,因此可能不是最优的。有更好的方法吗?

这里有两种方法,使用:

  • OpenCV
    cv2.flip()
  • Numpy
    np.fliplr()
  • 导入包

    import cv2
    import numpy as np
    
    我有一个numpy阵列中的三个图像,每个图像的分辨率如下所示:

    images.shape
    (3, 200, 400, 3)
    
    使用Jupyter的
    %%timeit
    模块: 运行以下代码可确保结果相同:

    x = [cv2.flip(images[i], 1) for i in range(3)]
    y = [np.fliplr(images[i]) for i in range(3)]
    
    for i in range(3):
        print(np.array_equal(x[i], y[i]))
    
    # True
    # True
    # True
    

    因此numpy的速度大约是opencv的20倍

    您可以简单地使用
    切片
    翻转最后一个轴,以将等效的翻转视图放入图像的输入数组中,这样就不会在内存中创建任何新数据,因此是一个高效的数据,就像这样-

    images[...,::-1,:]
    
    如果您仍然需要制作副本,请在那里使用
    .copy
    ,这仍然比
    np.fliplr
    更有效,并且对于小/适当大小的阵列更为明显

    运行时测试-

    看起来NumPy是赢家,所以我会用它来测试

    In [64]: images = np.random.randint(0,255,(3,200,400,3))
    
    In [65]: out1 = np.array([np.fliplr(images[i]) for i in range(3)])
    
    In [66]: out2 = images[...,::-1,:]
    
    In [67]: np.allclose(out1, out2)
    Out[67]: True
    
    In [68]: %timeit np.array([np.fliplr(images[i]) for i in range(3)])
    1000 loops, best of 3: 1.38 ms per loop
    
    In [69]: %timeit images[...,::-1,:]
    1000000 loops, best of 3: 259 ns per loop # virtually free
    
    如果你需要复印件-

    In [76]: images = np.random.randint(0,255,(3,10,10,3))
    
    In [77]: %timeit np.array([np.fliplr(images[i]) for i in range(3)])
    100000 loops, best of 3: 5.76 µs per loop
    
    In [78]: %timeit images[...,::-1,:].copy()
    100000 loops, best of 3: 2.23 µs per loop
    
    In [79]: images = np.random.randint(0,255,(3,100,100,3))
    
    In [80]: %timeit np.array([np.fliplr(images[i]) for i in range(3)])
    10000 loops, best of 3: 159 µs per loop
    
    In [81]: %timeit images[...,::-1,:].copy()
    10000 loops, best of 3: 152 µs per loop
    

    图像是如何存储的?作为数组列表或一个大数组?存储为单个
    .jpg
    文件。对于下面我自己的尝试,我在开始时使用
    matplotlib.image.imread()
    将它们读入一个numpy数组。你的答题帖中有
    图像
    。那么,
    images
    是一个数组还是一个列表呢?啊,好吧-三个图像在一个numpy数组中。我已经把
    形状添加到我的答案中。@scharette是的,你可以马上回答。因此,这是为了帮助未来的用户。如果你在一个问题上挣扎了一段时间,但在这里找不到答案,然后自己解决,然后你可以问一个问题,并打算自己回答。帮助中心有一条说明,在@scharette回答你自己的问题是可以的。显然,问题和答案必须是高质量的,而且以前从未被问过。可能会感兴趣,太好了!我也测试过了<代码>%timeit-r 10-n 100000个图像[…,::-1,:]
    。每个回路369纳秒±125纳秒(10次运行的平均值±标准偏差,每个100000个回路)。对于像我这样不熟悉三点(省略号对象)的其他人,这里有一些提示:,感谢提供额外的
    copy
    信息。另外,我也接受了,因为我不相信我们可以免费打败它同样值得一看的是,它只是一个切片的简写,带有额外的检查
    In [76]: images = np.random.randint(0,255,(3,10,10,3))
    
    In [77]: %timeit np.array([np.fliplr(images[i]) for i in range(3)])
    100000 loops, best of 3: 5.76 µs per loop
    
    In [78]: %timeit images[...,::-1,:].copy()
    100000 loops, best of 3: 2.23 µs per loop
    
    In [79]: images = np.random.randint(0,255,(3,100,100,3))
    
    In [80]: %timeit np.array([np.fliplr(images[i]) for i in range(3)])
    10000 loops, best of 3: 159 µs per loop
    
    In [81]: %timeit images[...,::-1,:].copy()
    10000 loops, best of 3: 152 µs per loop