【问题标题】:Can I read a specific image row using libjpeg?我可以使用 libjpeg 读取特定的图像行吗?
【发布时间】:2010-09-09 20:41:20
【问题描述】:

如果可能,使用 libjpeg,我想从 JPEG 图像的中间读取一行,而不读取前面的所有行。这个可以吗?

【问题讨论】:

  • 如果你的意思是直接从文件中获取,没办法。 JPEG 格式被高度压缩,因此您不能只拉出一行而不需要解压缩整个文件。
  • 我担心可能是这种情况,尽管我曾希望 JPEG 压缩可能偶尔会重置,从而允许乱序读取。查看 libpng,它似乎也只允许顺序访问。那么,我假设 PNG 也不能随机读取?
  • PNG 可能更适合随机访问,但前提是不使用其无损压缩模式。大多数图像处理库都认为文件 I/O 是作为填充和存储帧缓冲区的一种方式完成的,并且所有实际处理都是在 RAM 中包含整个图像的未压缩缓冲区上完成的。问题在于缓冲区的组织细节。

标签: c jpeg libjpeg


【解决方案1】:

答案几乎肯定是“可以,但需要付出比你想要的更多的努力”。

JPEG 图像是一个标记流,其中包含整个压缩图像的全局信息或与图像特定部分相关的信息。压缩通过将图像分解为颜色平面,可能将颜色空间更改为可以对颜色信息进行下采样的颜色空间,并在每个平面内对 8x8 像素块进行操作。

例如,如果压缩图像的大小使得它仅由整个块组成,则可以将压缩图像旋转 90 度,方法是仅转置基本块和每个块内的系数;即不解压缩、旋转真实图像和重新压缩。

鉴于此,您的方法是在进入库的过程中解析标记流,传递图像的所有全局标记,修改与图像大小相关的任何标记,并删除包含裁剪范围之外的系数的标记矩形。

如果对完成基本块的裁剪限制太粗,您可能需要进一步裁剪结果。

我不清楚的是,是否有任何真正胜过替代方案的方法,即在结果从库中出来时对其进行裁剪。该库是高度可配置的,因此您可以提供一个未压缩的数据消费者函数,该函数会丢弃裁剪矩形之外的所有像素,只保存您想要保留的像素。

【讨论】:

  • 感谢您的详细评论。我认为你是对的,与简单地处理 libjpeg 的输出相比没有什么优势。我最初的想法是将图像保留在磁盘上,然后仅加载和绘制特定的图块。最后,我认为更好的方法是一次处理一行源文件,在磁盘上生成缓存切片,并根据需要加载这些切片。
  • @Michael Cooper,这对我来说很有意义。您可以使用多分辨率金字塔,按需填充切片,缓存回磁盘。我相信这基本上就是 Adob​​e Light Room 在其缩略图缓存中所做的事情,例如,每个分辨率都在一个单独的文件中。
猜你喜欢
  • 2011-09-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-05-29
  • 1970-01-01
  • 1970-01-01
  • 2016-03-11
  • 2012-06-29
相关资源
最近更新 更多