首页 > 其他分享 >JPEG格式研究——(2)JPEG文件格式

JPEG格式研究——(2)JPEG文件格式

时间:2024-09-04 22:36:30浏览次数:4  
标签:哈夫曼 16 JPEG TAG 文件格式 FF 长度 格式

JPEG文件除了图像数据之外,还保存了与图片相关的各种信息,这些信息通过不同类型的TAG存储在文件中。

TAG

JPEG通过TAG标记压缩书记之外的信息。所有的TAG都包含一个TAG类型,TAG类型大小为两个字节,位于一个TAG的最前面。TAG类型的第一个字节一定为0xFF

以下是部分常见的TAG类型

TAG类型 数值 备注
SOF0 ~ SOF3
SOF5 ~ SOF7
SOF8 ~ SOF11
SOF13 ~ SOF15
FF C0 ~ FF C3
FF C5 ~ FF C7
FF C8 ~ FF CB
FF CD ~ FF CF
不同的编码模式对应不同的SOF,详见JPEG标准Table B.1。本文以常见的SOF0为研究对象
DHT FF C4 Define Huffman table(s),定义了解码所需的哈夫曼表
RSTm FF D0 ~ FF D7 遇到时重置DC系数,数字会递增,具体含义不清楚
SOI FF D8 Start of Image,表示图像文件的开始
EOI FF D9 End of Image,表示图像文件结束
SOS FF DA Start of scan,表示这一个TAG后就是压缩的图像数据,记录了DHT、DQT与图像不同部分的对应关系
DQT FF DB Define quantization table(s),定义了解码所需的量化表
APP0 ~ APP15 FF E0 ~ FF EF 应用保存的图片相关信息(如相机信息等)

JPEG文件中各种数据的分布

压缩数据中也是存在TAG的,虽然大部分TAG都在文件开头,但是也有少部分是例外。如EOI就在文件的末尾,RSTm会出现在压缩数据当中。

那么问题来了,如果压缩数据中有一个字节本身就是0xFF怎么办?JPEG的做法是在0xFF后面再加一个字节0x00,用于表示这不是一个TAG。

因为不知道解码需要哪些TAG,我在尝试写JPEG解码器的时候耗费了大量的时间在研究TAG上。总结出对于常见的JPEG图片解码需要的TAG:

1.SOI和EOI:用于确定文件的开头和结尾

2.DQT和DHT:保存了解码时需要用到的哈夫曼表和量化表

3.SOS:保存了图片不同部分的需要用哪个哈夫曼表

4.SOF:图片的长和宽、采样精度等、使用哪个量化表都保存在SOF中

5.RST:部分图片存在RST,遇到RST时要重置DC系数才能得到正确的图像

哈夫曼表与量化表

这里有个小坑,我原先一直以为DQT和DHT都是一个TAG对应一个表,后来发现一个TAG可以不只一个表

哈夫曼表

哈夫曼表的存储格式如下:

DHT格式

名称 长度(bit) 备注
$Lh$ 16 表示这一个TAG的长度(包括TAG类型的两个字节)
$Tc$ 4 Table class,0=DC表,1=AC表
$Th$ 4 Huffman table destination identifier,表示该哈夫曼表的id
$L_i$ 8 表示这一长度的编码个数
$V_{i,j}$ 8 表示编码前的原始数据

一个DHT中的哈夫曼表个数可以通过长度Lh算出:

$$
Lh = 2 + \sum_{t=1}^{n} (17+m_t)
$$

其中

$$
m_t=\sum_{1}^{16} L_i
$$

除了TAG类型和Lh一个TAG只有一个外,其余的都是每个哈夫曼表都有的。

Th之后是一个长度为16字节的数组,分别对应长度从1bit到16bit的编码个数。

再之后存的是各个编码对应的原始数据(以字节为单位)。JPEG采用的范式哈夫曼编码,可以这些信息推导出数据编码前后的对应关系。

量化表

DQT的结构与DHT结构相似,比DHT还稍微简单一些
DQT格式

名称 长度(bit) 备注
Lq 16 与Lh意义相同,表示这一TAG的长度
Pq 4 量化表的精度,0=8bit,1=16bit
Pq 4 量化表的id
Qk 8 量化表中的数据

量化表大小固定为8x8,也就是一个表有64个数,DQT长度与量化表个数也有类似的关系:

$$
Pq = 2 + \sum_{t=1}^n (65 + 64 \times Pq(t))
$$

SOF

SOF(Start of Frame) TAG的结构如下:

SOF格式

名称 长度(bit) 备注
Lf 16 这一TAG的长度
P 8 采样精度
Y 16 图片的高度
X 16 图片的宽度
Nf 4 Component的个数

Component的结构如下:

名称 长度(bit) 备注
Ci 8 Compoenent的id
Hi 4 水平缩放因子
Vi 4 垂直缩放因子
Tqi 8 对应的量化表id

根据我的理解,这里的Component个数相当于色度分量的个数,比如RGB和YUV都是3,灰度图像则是1.

SOS

SOS格式

名称 长度(bit) 备注
Ls 16 这一TAG的长度
Ns 8 一个scan内的component数量
Ss 8 没用
Se 8 没用
Ah 4 没用
Al 4 没用

Scan中还描述了这一Scan内不同Component中哈夫曼表和量化表的对应关系:

名称 长度(bit) 备注
Csi 8 通过id选择Component
Tdi 4 通过id选择DC哈夫曼表
Tai 4 通过id选择AC哈夫曼表

到这里JPEG解码所需要的几个重要TAG的结构就介绍完了,接下来就做好准备工作就可以开始解码了。


参考资料

JPEG解码系列博客:多媒体-编解码 - 随笔分类 - OnlyTime_唯有时光 - 博客园 (cnblogs.com)

JPEG标准:Microsoft Word - T081E.DOC (w3.org)

一个Rust写的JPEG解码器:MROS/jpeg_tutorial: 跟我寫 JPEG 解碼器 (Write a JPEG decoder with me) (github.com)

友情链接

我学习过程中写的JPEG图片查看器:Ryan1202/my-tiny-jpeg-viewer: A Tiny Jpeg Viewer (github.com)

标签:哈夫曼,16,JPEG,TAG,文件格式,FF,长度,格式
From: https://www.cnblogs.com/Ryan1202/p/18397454

相关文章

  • 修改iphone图片格式(heic转换格式)
    大家都知道,自从iOS11开始,iPhone图片默认格式是heic格式,虽然它体积更小,画质也更高一些,但是仍然有使用不方便的地方,比如有些网站、平台不支持上传.heic,发送给朋友,朋友无法直接查看图片等情况,那么我们该如何修改iPhone默认的图片格式呢?今天分享设置方法:打开iPhone中的【设置】功......
  • 【Python基础】数据格式化
    1.1数据的分类(基于维度)根据组织数据时与数据有联系的参数的数量,数据可以分为以下三类。(1)一维数据1.一维数据是具有对等关系的一组线性数据,对应数学中的集合、一维数组。2.在Python中,一维列表、一维元组、一维集合都是一维数据。3.可通过逗号、空格等符号分隔一维......
  • print格式化显示
    在Python中,`print`函数可以使用多种格式化方法来输出字符串。以下是几种常见的格式化方法及其用法:###1.使用`%`操作符这种方法是Python中较早的格式化字符串的方法,使用`%`操作符。```pythonname="Alice"age=30print("Mynameis%sandIam%dyearsold."%(......
  • 计算机领域的那些文件格式
    压缩文件格式1.001开发人:不特定公司:不适用主要用途:用于将大文件分卷成多个小文件,通常与`.002`,`.003`等文件一起使用。常见于老旧的分卷工具,如HJ-Split。2.bz2开发人:JulianSeward公司:不适用主要用途:用于压缩单个文件,通常用于UNIX和Linux......
  • python-pptx将多个ppt文件按照给定模板ppt格式整合
    frompptximportPresentationfrompptx.enum.shapesimportMSO_SHAPE_TYPEpr=Presentation('周彤.pptx')forslideinpr.slides:forshapeinslide.shapes:ifshape.shape_type==MSO_SHAPE_TYPE.TEXT_BOX:print(shape.text_frame.font.name,end='......
  • 【全网独家】OpenCV: 影像格式(Mat)
    OpenCV:影像格式(Mat)介绍在OpenCV中,Mat是一个非常重要的数据结构,用于表示二维的图像数据。它能够支持多种类型的数据存储,包括灰度图、彩色图以及多通道图像。特点多维矩阵:支持多维度矩阵操作。高效内存管理:使用引用计数来确保内存资源安全且高效地释放。灵活性:......
  • [数据集][目标检测]轮胎缺陷检测数据集VOC+YOLO格式2154张4类别
    数据集格式:PascalVOC格式+YOLO格式(不包含分割路径的txt文件,仅仅包含jpg图片以及对应的VOC格式xml文件和yolo格式txt文件)图片数量(jpg文件个数):2154标注数量(xml文件个数):2154标注数量(txt文件个数):2154标注类别数:4标注类别名称:["debris","ground","side","side_cut"]......
  • 经纬度格式转换-(互转 度转度分秒 度分秒转度……)
    经纬度格式分为三种:度:             (ddd.ddddd°)                十进制小数部分(5位)               百度地图,谷歌地图,手机自带gps经纬度输出度.分:      (ddd°mm.mmm’)            十进制小数部分(3位)  ......
  • Java中用于格式化文本消息的工具类MessageFormat.format,使用{x}占位符
    MessageFormat.format 是Java中用于格式化文本消息的工具类。它允许你定义一个模板字符串,并使用一组参数来填充模板中的占位符。这个类是用于处理复杂消息格式的,例如多语言环境下的消息。MessageFormat.format 的使用方式如下:publicstaticStringformat(Stringpattern,......
  • 通过命令行在阿里云服务器向MySQL上传CSV格式的表
    前言:由于不知道为什么,IDEA中没法导出sql格式的表,只能导出csv格式的,研究半天,记录一下历程。注意,sql文件包含SQL语句,如创建表、插入数据等,它能定义数据库结构并填充数据。csv文件是纯文本文件,通常用于存储表格数据,每行代表一条记录,字段之间用逗号分隔。也就是说,要向服务器导入......