我正在使用约20000 x 20000像素的1gb大tiff图像。我需要从图像中的任意位置提取几个图块(大约300x300像素)。

我尝试了以下解决方案:

  • Libtiff(我可以找到的唯一低级库)提供TIFFReadline(),但这意味着可以读取大约19700个不必要的像素。
  • 我实现了自己的tiff阅读器,该阅读器从图像中提取出一个图块,而无需读取不必要的像素。我期望它会更快,但是对图块的每一行进行一次搜索会使它非常慢。我还尝试将包含图块的文件的所有行读入缓冲区,然后从缓冲区中提取图块,但结果大致相同。

  • 我想收到可以改善我的图块提取工具的建议!

    一切都受到欢迎,也许您可​​以提出一个我可以使用的更高效的库,一些有关C/C++ I/O的技巧,一些满足我需求的更高级别的策略,等等。

    问候,
    胡安

    最佳答案

    [主要编辑2010年1月14日]

    当您未对tiff进行平铺时,我对您提到的平铺感到有些困惑。

    我确实使用平铺/金字塔形TIFF图像。我已经用VIPS创建了那些

    vips im_vips2tiff source_image output_image.tif:none,tile:256x256,pyramid
    

    我认为您可以使用以下方法执行此操作:
    vips im_vips2tiff source_image output_image.tif:none,tile:256x256,flat
    

    您可能要尝试使用磁贴大小。然后,您可以使用TIFFReadEncodedTile进行阅读。

    如果需要放大/缩小,使用金字塔形tiff的多分辨率存储会更快。您可能还想使用它来获得几乎立即带有详细图片的粗糙图像。

    切换到(适当大小的)切片存储之后(这将为您带来随机访问带来的巨大性能提升!),您的瓶颈将是磁盘io。如果按顺序读取文件,则读取速度要快得多。在这里映射可能是解决方案。

    一些有用的链接:

    VIPS
    IIPImage
    LibTiff.NET stackoverflow
    VIPS是一个图像处理库,它不仅可以执行读/写操作,还可以做更多的事情。它具有自己的非常有效的内部格式。它有很好的算法文档。首先,它使处理与文件系统脱钩,从而允许对切片进行缓存。

    IIPImage是一个多缩放Web服务器/浏览器库。我发现该文档是有关多分辨率成像的很好的信息来源(例如Google map )

    本页上的另一个解决方案,使用mmap,仅对“小”文件有效。我经常碰到32位边界。通常,由于32位操作系统(安装了4 GB RAM)在1位字节的内存上分配内存将失败,原因是一个或两个应用程序运行后,甚至虚拟内存也会崩溃。仍然有足够的内存来缓存部分或整个图像。更多的内存=更多的性能。

    关于c++ - 高效的TIFF瓦片提取C++,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/1651214/

    10-12 12:42
    查看更多