【问题标题】:How to estimate size of a Jpeg file before saving it with a certain quality factor?如何在以特定质量因子保存 Jpeg 文件之前估计其大小?
【发布时间】:2009-11-16 06:37:32
【问题描述】:

我有一个 24 位的位图,我正在用 C++、MFC 编写应用程序, 我正在使用 libjpeg 将位图编码为 24 位 jpeg 文件。

当此位图的宽度为M,高度为N时。

如何在以一定的品质因数 N (0-100) 保存之前估计 jpeg 文件的大小。

可以这样做吗?

例如。 我想实现一个滑动条,它代表保存具有特定质量因子 N 的当前位图。 旁边有一个标签。显示使用此品质因数解码位图时的近似文件大小。 当用户移动滑动条时。他可以大致预览要保存的jpeg文件的文件大小。

【问题讨论】:

  • 保存 JPG 需要多长时间?您可以将其“保存”到内存中(可能在另一个线程中),然后从中获取其大小吗?如果它真的很快,您可能可以完成整个过程,但不要将任何内容写入磁盘。至少对于小图像。对于较大的,猜测(无法帮助您)。

标签: jpeg


【解决方案1】:

在 libjpeg 中,您可以编写一个自定义目标管理器,它实际上并不调用 fwrite,而只是计算写入的字节数。

从 jdatadst.c 中的 stdio 目标管理器开始,并查看 libjpeg.doc 中的文档。

您的init_destinationterm_destination 方法将非常少(只是alloc/dealloc),而您的empty_output_buffer 方法将进行实际计数。完成 JPEG 写入后,您必须从自定义结构中读取计数值。确保在调用 term_destination 之前执行此操作。

【讨论】:

  • 非常感谢亚当。我知道了。我正在使用基于 libjpeg 的 FreeImage 库,它具有内置 API。我会用它
【解决方案2】:

这还取决于您使用的压缩方式,更具体地说,您使用的每个颜色像素有多少位。

品质因数在这里对您没有帮助,因为品质因数 100 的范围(在大多数情况下)从每个颜色像素 6 位到每个颜色像素约 10 位,甚至可能更多(不确定)。

所以一旦你知道它从那里开始真的很直接......

【讨论】:

  • 我想保存为 24bits jpeg 文件
  • 你应该最感兴趣的是压缩率而不是图像的位深度。换句话说,现在大多数图像都使用 24 位深度,转换为 R = 8 位、G = 8 位和 B = 8 位 (RGB)。现在要首先计算图像大小,您需要以百万像素 MP 为单位的大小,基本上是宽度乘以图像的高度。然后要获得以字节为单位的大小,您将 MP 中的大小乘以位深度并除以 8 .. 在您的情况下为 (N * M * 24)/8。这将为您提供与原始 BMP 相同的图像的原始大小。
  • 您必须将其除以压缩比。例如,如果您的压缩比为 4:1,这意味着您将除以 4,使等式如下所示:((N * M * 24)/8)/4
  • 请记住,JPEG 转换不是无损的,因此必须在某处进行转换,并且可能由质量因素决定。
  • 这就是为什么您使用组件信息中的子采样进行估计的原因,正如我所描述的那样,它还揭示了每个组件的位数。
【解决方案3】:

如果您知道子采样因子,则可以进行估算。该信息来自帧标记的开始。

在宽度和高度之前的同一标记中,位深度也是如此。

如果你让

int subSampleFactorH = 2, subSampleFactorV = 1;

然后

int totalImageBytes = (Image.Width / subSampleFactorH) * (Image.Height / subSampleFactorV);

然后您还可以选择添加更多字节来考虑容器数据。

int totalBytes = totalImageBytes + someConstantOverhead;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-08-03
    • 2011-12-16
    • 1970-01-01
    • 1970-01-01
    • 2011-06-02
    • 1970-01-01
    • 2016-02-22
    相关资源
    最近更新 更多