【问题标题】:how to read a large image by lines with python如何使用python逐行读取大图像
【发布时间】:2021-12-23 05:50:09
【问题描述】:

我正在尝试处理一些大小超过 1G 的卫星照片。我用python写代码,这些方法我都试过了。

image = np.array(io.imread(each_dir))
image = np.array(TiffImagePlugin.open(each_dir))
image = np.array(Image.open(each_dir))

只有io.read适用于200Mb大小的照片,大于1G时会报错 MemoryError: Unable to allocate 17.1 GiB for an array with shape (156105, 39136, 3) and data type uint8

我已将 RAM 从 16g 更改为 32g,但这不起作用。所以我想问有没有一种方法可以逐行读取 imgae 而不是一次读取整个图像? 非常感谢。

【问题讨论】:

    标签: python tiff satellite


    【解决方案1】:

    我建议您在开始之前将相当大的 TIFF 平铺在 Python 之外。大量借鉴约翰 (@jcupitt) 的回答 here,您可以使用 vips 来做到这一点。

    我在终端中创建了一个 39100x156100 TIFF,并使用 vips 的 “DeepZoom Save” 功能平铺了它:

    vips dzsave big.tif outdir --depth one --tile-size 8192 --overlap 0 --suffix .tif
    

    它花费了 38 秒和 2GB 的 RAM,因此非常节俭。下面是它生成的图块及其元数据的列表。

    结果

    0_0.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_10.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_11.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_12.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_13.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_14.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_15.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_16.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_17.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_18.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_19.tif TIFF 8192x452 8192x452+0+0 8-bit sRGB 10.594MiB 0.000u 0:00.000
    0_1.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_2.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_3.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_4.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_5.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_6.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_7.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_8.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    0_9.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_0.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_10.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_11.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_12.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_13.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_14.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_15.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_16.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_17.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_18.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_19.tif TIFF 8192x452 8192x452+0+0 8-bit sRGB 10.594MiB 0.000u 0:00.000
    1_1.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_2.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_3.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_4.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_5.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_6.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_7.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_8.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    1_9.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_0.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_10.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_11.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_12.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_13.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_14.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_15.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_16.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_17.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_18.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_19.tif TIFF 8192x452 8192x452+0+0 8-bit sRGB 10.594MiB 0.000u 0:00.000
    2_1.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_2.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_3.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_4.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_5.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_6.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_7.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_8.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    2_9.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_0.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_10.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_11.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_12.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.010u 0:00.000
    3_13.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_14.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_15.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_16.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_17.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_18.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_19.tif TIFF 8192x452 8192x452+0+0 8-bit sRGB 10.594MiB 0.000u 0:00.000
    3_1.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_2.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_3.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_4.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_5.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_6.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_7.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_8.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    3_9.tif TIFF 8192x8192 8192x8192+0+0 8-bit sRGB 192.001MiB 0.000u 0:00.000
    4_0.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_10.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_11.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_12.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_13.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_14.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_15.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_16.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_17.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_18.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_19.tif TIFF 6332x452 6332x452+0+0 8-bit sRGB 8.18867MiB 0.000u 0:00.000
    4_1.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_2.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_3.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_4.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_5.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_6.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_7.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_8.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    4_9.tif TIFF 6332x8192 6332x8192+0+0 8-bit sRGB 148.407MiB 0.000u 0:00.000
    

    另一种完全不同的方法可能是使用 stream 命令,它是 ImageMagick 套件的一部分 - 也在 Python 之外。因此,我制作了一个名为 big.tif 的 50,000x50,000 像素 RGB TIFF,然后将底部 1/5(即第 40,000 行以上)流式传输到 RGB888 原始文件中,如下所示:

    magick stream -map rgb -storage-type char -extract 50000x10000+0+40000 big.tif bottom.dat
    

    该命令在我的 Mac 上运行大约 18 秒。然后,您可以将其读入 Python 中的 Numpy 数组,如下所示:

    import numpy as np
    
    # Load RGB888 file and reshape back to its correct shape
    im = np.fromfile('bottom.dat', dtype=np.uint8).reshape((10000,50000,3))
    

    如果您不熟悉 ImageMagick 的几何规范,上面命令中的 50000x10000+0+40000 部分表示 “提取一个 50,000 像素宽 x 10,000 像素高的区域,其左上角角距左边缘 0 像素,距顶部 40,000 像素"

    【讨论】:

    • 非常感谢。我尝试了vips 的第一个解决方案,这对我有用。唯一的区别是我收到了很多警告,比如(vips:3844): VIPS-WARNING **: 21:11:55.984: Unknown field with tag 33550 (0x830e) encountered
    • 标签 33550 是 vips 不知道的 GeoTIFF 文件的特定标签,因此已被忽略。这里有一个可搜索的标签列表awaresystems.be/imaging/tiff/tifftags/…
    • 是的,我正在处理 GeoTIFF 文件。通过在您提供的网站上进行搜索,我发现类似于 Tag 33550 的警告与 GeoTIFF 文件中的额外信息有关。非常感谢。
    【解决方案2】:

    您可以使用pyvips 读出平铺的 TIFF 的一部分。例如:

    import pyvips
    
    image = pyvips.Image.new_from_file("huge-tiled-image.tiff")
    tile = image.crop(100, 110, 1000, 1000)
    tile = image.crop(8000, 6500, 1000, 1000)
    ...
    

    其中四个数字分别是左、上、宽和高,以像素为单位。它速度非常快,您可以读取任何您喜欢的区域,它只会解码您要求的图像部分,并且会保留最近解压缩的像素缓存。

    你可以在pyvips中做进一步的处理,或者将像素渲染到一个数组中交给numpy,见:

    https://libvips.github.io/pyvips/intro.html#numpy-and-pil

    【讨论】:

    • 非常感谢。我发现conda 安装不起作用,我用pip 安装它。这很好用。
    猜你喜欢
    • 1970-01-01
    • 2020-11-12
    • 2018-12-08
    • 2014-04-04
    • 2011-12-22
    • 1970-01-01
    相关资源
    最近更新 更多