Amy*_*ens 6 python interpolation numpy scipy
目前,我已经编写了一些插入管道的Python代码.
传入的数据形状为numpy数组(1,512,19,25).我使用它scipy.ndimage.interpolation.zoom来使阵列形状(1,512,38,50).这可以通过一次调用函数来完成.基本上,它将每个(19,25)件调整为大小(38,50).
稍后在代码中,当数据以另一种方式移动时,不同的数据再次在另一个方向(38,50)到(19,25)上调整大小.
一切都按实施的方式运作,但我发现这确实很慢.例如,我测试了scipy.ndimage.interpolation.zoom调整图像文件大小的函数,它比Matlab的imresize函数慢.
有什么更快的方法在Python中执行此操作?
太长了;查看 Skimage 的Pyramid_Gaussian。在 (512, 512) 的单个图像上,它显示了 0.3M 倍的加速量级。(163 毫秒/471 纳秒 = 346072)。Pillow-SIMD可以超快速地重新采样/调整大小,但需要您在安装之前卸载 PIL、Pillow。它使用并行处理(单指令、多数据 - SIMD)和更好的算法,例如用顺序框替换基于卷积的高斯模糊。建议在设置单独的venv.
有多种方法可以对图像进行上采样和下采样。我将添加一些我使用过的方法的基准。当我遇到更多方法时,我会不断更新这个答案,以便这可以作为其他人的参考。
\n#Utility function for plotting original, upsampled, and downsampled image\n\ndef plotit(img, up, down):\n fig, axes = plt.subplots(1,3, figsize=(10,15))\n axes[0].imshow(img)\n axes[1].imshow(up)\n axes[2].imshow(down)\n axes[0].title.set_text(\'Original\')\n axes[1].title.set_text(\'Upsample\')\n axes[2].title.set_text(\'Downsample\')\nRun Code Online (Sandbox Code Playgroud)\nIIUC,这在某种程度上是你的管道 -
\nfrom scipy.ndimage import zoom\nfrom skimage.data import camera\n\nimg = camera() #(512,512)\nup = zoom(img,2) #upsample image\n\n#some code\n...\n\ndown = zoom(up,0.5) #downsample the upsampled image\n\nplotit(img, up, down)\nRun Code Online (Sandbox Code Playgroud)\n\n方法和基准\n(in no specific order)
1.Scipy缩放(阶数=3)
\n使用给定阶数的样条插值来缩放数组,在本例中,默认阶数为 3。
\n%%timeit\n#from scipy.ndimage import zoom\nup = zoom(img,2)\ndown = zoom(up,0.5)\n\n#163 ms \xc2\xb1 12.1 ms per loop (mean \xc2\xb1 std. dev. of 7 runs, 10 loops each)\nRun Code Online (Sandbox Code Playgroud)\n2.Scipy缩放(order=0)
\n使用给定阶数的样条插值来缩放数组,在本例中,阶数 = 0。
\n%%timeit\n#from scipy.ndimage import zoom\nup = zoom(img,2, order=0)\ndown = zoom(up,0.5, order=0)\n\n#18.7 ms \xc2\xb1 950 \xc2\xb5s per loop (mean \xc2\xb1 std. dev. of 7 runs, 100 loops each)\nRun Code Online (Sandbox Code Playgroud)\n\n在高斯金字塔中,后续图像使用高斯平均值(高斯模糊)进行加权并按比例缩小。对图像应用高斯模糊与使用高斯函数对图像进行卷积相同。模糊量取决于标准差大小 (sigma)。
\n%%timeit\n#from skimage.transform import import pyramid_gaussian\nup = pyramid_gaussian(img,2)\ndown = pyramid_gaussian(up,0.5)\n\n#471 ns \xc2\xb1 30.4 ns per loop (mean \xc2\xb1 std. dev. of 7 runs, 1000000 loops each)\nRun Code Online (Sandbox Code Playgroud)\n4. Skimage的pyramid_expand和pyramid_reduce
\n图像金字塔是一种多尺度图像表示,其中图像经过重复平滑和子采样。第一个函数对图像进行平滑处理,然后对图像进行上采样,而第二个函数则执行相同的操作,但会进行下采样,这两个函数默认都使用样条阶数 = 1。
\n%%timeit\n#from skimage.transform import import pyramid_expand, pyramid_reduce\nup = pyramid_expand(img,2)\ndown = pyramid_reduce(up,2)\n\n#120 ms \xc2\xb1 3.08 ms per loop (mean \xc2\xb1 std. dev. of 7 runs, 10 loops each)\nRun Code Online (Sandbox Code Playgroud)\n5.Skimage重新缩放
\n按特定因子缩放图像。对放大或缩小的 N 维图像执行样条插值(默认阶数=1)。请注意,缩小图像尺寸时应启用抗锯齿功能,以避免出现锯齿现象。
\n%%timeit\n#from skimage.transform import import rescale\nup = rescale(img,2)\ndown = rescale(up,0.5)\n\n#83 ms \xc2\xb1 3.69 ms per loop (mean \xc2\xb1 std. dev. of 7 runs, 10 loops each)\nRun Code Online (Sandbox Code Playgroud)\n\n返回此图像的调整大小的副本。从输入图像中选取一个最近的像素。忽略所有其他输入像素。
\n%%timeit\n#from PIL import Image\nim = Image.fromarray(img)\nup = im.resize((im.width*2, im.height*2),resample=Image.NEAREST)\ndown = up.resize((up.width//2, up.height//2),resample=Image.NEAREST)\n\n#704 \xc2\xb5s \xc2\xb1 29.7 \xc2\xb5s per loop (mean \xc2\xb1 std. dev. of 7 runs, 1000 loops each)\nRun Code Online (Sandbox Code Playgroud)\n7. PIL使用 BILINEAR滤波器调整大小以进行重采样
\n返回此图像的调整大小的副本。对于调整大小,对可能对输出值有贡献的所有像素使用线性插值来计算输出像素值。对于其他变换,使用输入图像中 2x2 环境上的线性插值。
\n%%timeit\n#from PIL import Image\nim = Image.fromarray(img)\nup = im.resize((im.width*2, im.height*2),resample=Image.BILINEAR)\ndown = up.resize((up.width//2, up.height//2),resample=Image.BILINEAR)\n\n#10.2 ms \xc2\xb1 877 \xc2\xb5s per loop (mean \xc2\xb1 std. dev. of 7 runs, 100 loops each)\nRun Code Online (Sandbox Code Playgroud)\n\n返回此图像的调整大小的副本。对于调整大小,对可能对输出值有贡献的所有像素使用三次插值来计算输出像素值。对于其他变换,使用输入图像中 4x4 环境的三次插值。
\n%%timeit\n#from PIL import Image\nim = Image.fromarray(img)\nup = im.resize((im.width*2, im.height*2),resample=Image.BICUBIC)\ndown = up.resize((up.width//2, up.height//2),resample=Image.BICUBIC)\n\n#12.3 ms \xc2\xb1 326 \xc2\xb5s per loop (mean \xc2\xb1 std. dev. of 7 runs, 100 loops each)\nRun Code Online (Sandbox Code Playgroud)\n\n返回此图像的调整大小的副本。使用高质量 Lanczos 滤波器(截断的 sinc)对可能对输出值有贡献的所有像素计算输出像素值。
\n%%timeit\n#from PIL import Image\nim = Image.fromarray(img)\nup = im.resize((im.width*2, im.height*2),resample=Image.LANCZOS)\ndown = up.resize((up.width//2, up.height//2),resample=Image.LANCZOS)\n\n#15.7 ms \xc2\xb1 184 \xc2\xb5s per loop (mean \xc2\xb1 std. dev. of 7 runs, 100 loops each)\nRun Code Online (Sandbox Code Playgroud)\n
| 归档时间: |
|
| 查看次数: |
1273 次 |
| 最近记录: |