# 图片压缩：从像素、预测与 DCT 到 JPEG、AVIF 和 JPEG AI

Author: Fanyi Pu

Published: 2026-09-21

Canonical: <https://pufanyi.com/blog/ml/notes/image-compression>

从一行像素亲手推导预测、熵编码、颜色采样、DCT 与量化，再理解 PNG、JPEG、WebP、AVIF、JPEG XL 和学习式图像编码。

一张 $4000\times3000$、每通道 8 bit 的 RGB 照片，若直接保存每个像素，需要

$$
4000\times3000\times3=36{,}000{,}000\ \text{bytes},
$$

也就是约 36 MB。可是真实照片里，蓝天相邻像素很像，墙面大面积平滑，颜色通道彼此相关；即使在文字边缘，出现什么差值也不是均匀随机的。图片压缩所做的事，是把这些**可以预测的重复**变成容易描述的符号，再决定哪些误差值得花 bits 保留。

本文不从格式排行榜开始，而是完整走一遍 encoder 与 decoder。我们会先构造一个完全可逆的压缩器，再允许它有控制地丢掉信息。走完以后，PNG、JPEG、WebP、AVIF、JPEG XL 与学习式 codec 就不再是几个孤立名字，而是对同一组问题的不同回答。

## 压缩前先明确：一张图片到底是什么

最简单的 raster image 是一个规则网格。每个位置保存若干 sample，例如 RGB 三个颜色通道；文件还需要说明宽高、bit depth、颜色空间、透明度与元数据。所谓「原始 36 MB」只计算了像素数组，并不意味着任何 `.raw` 文件恰好这么大。

压缩有三种常见目标：

- **Lossless**：解码后每个 sample 与原值完全相同，适合截图、线稿、索引图、需要继续编辑或数据必须精确的场景；
- **Lossy**：允许 sample 改变，以显著减少 bits，照片和网络媒体常用；
- **Visually lossless**：肉眼在给定观看条件下难以分辨差异，但它仍然是有损目标，不保证逐 sample 相同。

这一区分很重要。「看起来一样」不能推出「数据一样」；反过来，lossless 也不保证文件一定小。压缩率取决于图像里是否存在编码器能利用的结构。

## 第一步：不保存像素本身，保存它与预测的差

先只看一行 8-bit 灰度值：

$$
x=[52,53,54,55,55,56,57,57].
$$

若直接保存，每个数仍在 0 到 255 之间。现在约定第一个值原样保存，此后都用左边已经重建的值预测当前值：

$$
e_0=x_0,
\qquad
e_i=x_i-x_{i-1}.
$$

得到

$$
e=[52,1,1,1,0,1,1,0].
$$

这一步没有减少元素数量，也没有丢失信息。Decoder 从 $\hat x_0=e_0$ 开始，重复 $\hat x_i=\hat x_{i-1}+e_i$，就能精确恢复原行。变化只在统计分布：原像素分散在 52 到 57，residual 却几乎全是 0 和 1。

一行像素经过左侧预测变成 residual

原始像素为 52 到 57。第一个值原样保存，后续值减去左邻居后，五个 residual 为 1，两个为 0，decoder 用逐项相加精确重建原行。

原始像素 x

52

53

54

55

56

57

首项原样；其后减左邻居

residual e

1

0

residual 频数

1 次

5 次

2 次

常见符号可分配更短的 code

decoder：x̂₀=e₀，x̂ᵢ=x̂ᵢ₋₁+eᵢ → 精确恢复

[View diagram in the original article](https://pufanyi.com/blog/ml/notes/image-compression)

Prediction 没有删除任何元素，而是把分布集中到 0 和 1；entropy coding 才利用频数差异减少 bits。首项 52 是建立预测所需的 side information，在更大图像中会被许多后续样本摊薄。

### 为什么 residual 会变成更少的 bits

如果仍给每个 residual 固定 8 bit，文件一点也没变小。真正利用这种集中分布的是 entropy coding：常见符号用短表示，罕见符号用长表示。一个概率为 $p(s)$ 的符号，其理想码长接近

$$
\ell(s)=-\log_2 p(s).
$$

分布的平均理论下界由 entropy 描述：

$$
H(X)=-\sum_s p(s)\log_2 p(s).
$$

因此 prediction 和 entropy coding 分工不同。前者把原始数据改写成更偏斜、更容易建模的分布；后者才把概率优势兑现为较少 bits。Prediction 选得不好时，residual 可能更杂，甚至压得更差。

PNG 就沿着这条无损路线工作。每条 scanline 可以在 None、Sub、Up、Average 与 Paeth 五种可逆 filter 中选择一种，把像素改写成相对左侧、上方或邻域预测的差；随后 DEFLATE 再用 LZ77 匹配与 Huffman coding 压缩字节流 ([World Wide Web Consortium, 2025](https://pufanyi.com/blog/ml/notes/image-compression#bib-w3c2025png))。Decoder 反向执行即可逐 sample 复原。PNG 不等于「任何图都压得小」：自然照片的细碎变化可能让无损 residual 仍然很复杂。

## 第二步：先把颜色放到更合适的坐标系

RGB 便于显示，却不总适合按视觉重要性分配 bits。照片与视频 codec 常把颜色变换为一个亮度样分量 $Y$ 和两个色度分量 $C_b,C_r$。这是一次坐标变换：它把大部分明暗结构与色彩差异分开，但**变换本身并不会减少 sample 数量**。

真正减少样本的是 chroma subsampling。对一个 $2\times2$ 区域：

- RGB 或 YCbCr 4:4:4 都有 $4\times3=12$ 个 samples；
- YCbCr 4:2:0 保留 4 个 $Y$，让四个位置共享 1 个 $C_b$ 与 1 个 $C_r$，共 6 个 samples。

RGB、YCbCr 4:4:4 与 YCbCr 4:2:0 的样本数量

一个 2 乘 2 区域在 RGB 和 YCbCr 4:4:4 中都有 12 个样本；4:2:0 保留四个亮度样本，只共享两个色度样本，共六个。

RGB

每像素 R + G + B

4 × 3 = 12 samples

color transform

YCbCr 4:4:4

每像素 Y + Cb + Cr

chroma

subsampling

YCbCr 4:2:0

四个 Y，共享一组 Cb / Cr

Y

Cb

Cr

4 + 1 + 1 = 6 samples

坐标变换不减样本；4:2:0 才在这里丢掉空间色度信息

[View diagram in the original article](https://pufanyi.com/blog/ml/notes/image-compression)

同一个 \$2\times2\$ 区域：YCbCr 只是重排颜色信息；4:2:0 才把 12 个 samples 减到 6 个。图中共享关系是采样结构示意，不规定具体的 chroma siting 或上采样 filter。

人类视觉通常对高频亮度变化比高频色度变化敏感，所以照片常能承受色度降采样。但文字、UI、像素画、彩色细线和继续编辑的素材可能出现明显 color bleeding。4:2:0 是有损操作；把 RGB 换成 YCbCr、却仍保留 4:4:4，则不能单凭名称断言有损。

## 第三步：把空间图样改写成频率

现在处理一个小图块。相邻像素往往一起缓慢变化，直接量化它们会分别制造误差。离散余弦变换（DCT）换一组基底描述同一块：一个系数表示整体平均，其他系数表示从水平缓变、垂直缓变到细密交替的不同空间频率。

对 $N\times N$、已经减去中心值的 block $f(x,y)$，二维 DCT 可以写成

$$
C(u,v)=\alpha(u)\alpha(v)
\sum_{x=0}^{N-1}\sum_{y=0}^{N-1}
f(x,y)
\cos\frac{(2x+1)u\pi}{2N}
\cos\frac{(2y+1)v\pi}{2N},
$$

其中 $alpha(0)=\sqrt{1/N}$，其余 $alpha(k)=\sqrt{2/N}$。$C(0,0)$ 是 DC coefficient，描述整块平均；$u$ 或 $v$ 越大，basis 变化越快，对应更高频的 AC coefficient。

为什么要绕这一圈？一块平滑的像素需要很多相近数值描述，但在 frequency domain 中，能量常集中于少数低频系数。正交 DCT 仍输出 $N^2$ 个 coefficients；若保留足够精度，它可以逆变换回来。**DCT 不是靠减少系数数量压缩，而是把信息搬到更适合随后取舍的位置。**

## 第四步：量化才真正决定丢掉什么

对每个 transform coefficient $C_k$ 选择 quantization step $Q_k$：

$$
q_k=\operatorname{round}\!\left(\frac{C_k}{Q_k}\right),
\qquad
\hat C_k=q_kQ_k.
$$

较大的 $Q_k$ 让更多小 coefficient 变成零，也让保留下来的 coefficient 更粗糙。Decoder 只能得到 $\hat C_k$，无法知道 rounding 前的 $C_k$；这里是典型 transform codec 的主要不可逆步骤。常见设计给高频更大的 step，因为细碎误差往往比低频亮度偏移不显眼。

下面的图使用同一份 $4\times4$ 数值，程序实际计算正交 DCT、逐频率量化与 inverse DCT。可以同时看到两件事：transform 前后数量都是 16；量化后出现大量零，而重建像素不再逐个相等。

四乘四像素块的 DCT、量化与重建

十六个源像素经过 DCT 后仍有十六个系数。逐频率量化使其中多个系数变成零，逆变换得到略有不同的十六个重建像素。

像素 x

82

83

84

86

87

91

96

108

88

110

140

DCT C（四舍五入显示）

-143

-36

10

-1

-32

29

-9

0

-10

4

-2

3

量化 q

2

-8

5

重建 x̂

85

81

90

95

112

89

111

138

DCT

q=round(C/Q)

有损

×Q, IDCT

DCT：16 pixels → 16 coefficients；量化后 8/16 为零

本例重建 MSE = 3.50；改变 Q 会同时改变 rate 与 distortion

[View diagram in the original article](https://pufanyi.com/blog/ml/notes/image-compression)

一个真实计算的微型例子。DCT 集中能量但不减少数量；frequency-dependent quantization 产生零和不可逆误差，后续扫描与 entropy coding 才能用短 bitstream 表示这些零。

JPEG 的 baseline sequential 流程正是这条经典路径：把图像分块，变换并量化，再让 DC difference 和按 zigzag 顺序排列的 AC coefficients 进入 run-length/Huffman coding ([Joint Photographic Experts Group, n.d.](https://pufanyi.com/blog/ml/notes/image-compression#bib-jpeg1992jpeg1))。Zigzag 让低频靠前、高频零更容易连成一段；entropy coding 只缩短符号表示，不会再改变重建画面。

把 decoder 写出来，有助于定位每种误差：

$$
\text{bits}
\to \hat q
\to \hat C
\to \hat f
\to \text{color upsampling/conversion}
\to \hat x.
$$

若 block 边界两侧的量化误差不连续，会看到 blocking；高频截断会在锐利边缘附近形成 ringing；色度降采样会让颜色越过边缘；低 bit depth 或过强低频量化可能产生 banding。所谓「压缩痕迹」不是一个单一现象，只有找到它来自哪一步，才知道该换 subsampling、quality、bit depth、encoder，还是格式。

图片编码与解码管线

编码器依次进行颜色处理、预测或变换、量化与熵编码。解码器反向熵解码、反量化、逆变换与颜色重建；量化和可选色度降采样是有损边界。

Encoder：让分布更集中，再决定舍弃多少

RGB samples

原始网格

颜色 / 采样

可选 4:2:0

预测 / DCT

集中分布

量化

控制失真

熵编码

概率 → bits

bitstream

重建 RGB

显示 / 保存

颜色重建

可选上采样

逆变换

加回预测

反量化

q × Q

熵解码

bits → symbols

常见有损边界：chroma subsampling 与 quantization；entropy coding 可逆

[View diagram in the original article](https://pufanyi.com/blog/ml/notes/image-compression)

一条典型 transform codec 的双向账本。Decoder 不会猜 encoder 的选择；bitstream 携带必要参数与量化后的符号。Lossless codec 也会预测和熵编码，只是不跨越图中的有损边界。

## 常见格式在这条链上怎样选择

格式名称不是单独的质量旋钮。同一格式可以有多个 encoder、速度 preset、颜色配置与质量档；不同格式的 `quality=80` 没有共同刻度。更有用的比较是问它如何预测、在哪里有损、怎样建模概率，以及目标 decoder 是否可用。

| 格式      | 主要机制                                              | 是否有损                | 更适合先考虑的场景                      |
| ------- | ------------------------------------------------- | ------------------- | ------------------------------ |
| PNG     | scanline filters + DEFLATE                        | lossless            | UI、截图、线稿、精确 alpha、需逐 sample 保留 |
| JPEG    | block DCT + quantization + entropy coding         | 主要是 lossy；标准也定义其他模式 | 兼容性优先的照片交付                     |
| WebP    | VP8 intra prediction/transform；另有独立 lossless mode | 两者皆可                | 现代 Web 照片、透明图与动画，需核对工具链        |
| AVIF    | HEIF 容器中的 AV1 image coding                        | 两者皆可                | 高效率照片、HDR/WCG、现代终端             |
| JPEG XL | lossy VarDCT 或 lossless Modular                   | 两者皆可                | HDR、渐进解码、专业图像或可控生态             |

WebP lossy 借用 VP8 的 intra prediction 与 transform coding，lossless 模式则使用不同的 reversible transforms、预测和 entropy coding ([Google for Developers, n.d.](https://pufanyi.com/blog/ml/notes/image-compression#bib-googlewebp))。AVIF 把 AV1 image content 封装在 HEIF 结构中，可表达 SDR、HDR、wide color gamut、多种 bit depth、静态图与 image sequence ([Alliance for Open Media, n.d.](https://pufanyi.com/blog/ml/notes/image-compression#bib-aomediaavif))。JPEG XL 同时设计了面向照片的 VarDCT 与面向无损/一般数据的 Modular 路径，并支持 progressive decoding、alpha、HDR 和 legacy JPEG 的 bit-exact reconstruction ([Joint Photographic Experts Group, 2023](https://pufanyi.com/blog/ml/notes/image-compression#bib-jpeg2023jxlwhitepaper))。

这里故意不宣布一个永恒赢家。标准已经发布，不等于所有浏览器、操作系统、CDN、编辑器和硬件都已支持；兼容性也会随时间变化。实际交付要从 decoder 端倒推，并用自己的内容实测。

## 怎样公平比较两个 encoder

只比较文件大小没有意义：把一张图压到几乎看不清，当然很小。应在多个 rate 点编码同一组有代表性的图片，画 rate–distortion curve。常见 rate 是 bits per pixel：

$$
\operatorname{bpp}=\frac{8\times\text{file bytes}}{W\times H}.
$$

Distortion 可以从 mean squared error 和 PSNR 开始：

$$
\operatorname{MSE}=\frac1n\sum_i(x_i-\hat x_i)^2,
\qquad
\operatorname{PSNR}=10\log_{10}\frac{L^2}{\operatorname{MSE}}.
$$

但 PSNR 不完全代表感知质量。严肃比较还应加入结构或感知指标，并亲自检查人脸、文字、暗部渐变、强边缘、噪声与透明边界。至少固定或记录：encoder 名称和版本、preset、chroma format、bit depth、颜色管理、metadata 是否计入，以及 decoder 输出如何对齐。跨 encoder 比较一个同名 quality 数值，通常不是控制变量。

## 学习式图像压缩把哪些步骤变成了网络

经典 codec 由工程师规定 transform、quantization table 与概率上下文。学习式 codec 可以让 analysis transform 把图像映射到 latent，让 entropy model 学习 latent 的概率，再由 synthesis transform 重建：

$$
y=g_a(x),
\qquad
\hat y=Q(y),
\qquad
\hat x=g_s(\hat y).
$$

若 entropy model 给出 $p(\hat y)$，预计 rate 近似

$$
R\approx-\sum_i\log_2 p(\hat y_i).
$$

训练目标仍是熟悉的 tradeoff：

$$
\mathcal L=R+\lambda D(x,\hat x).
$$

$\lambda$ 大时更愿意花 bits 降低 distortion；$\lambda$ 小时更偏向低 rate。早期 end-to-end 工作已经把 nonlinear transform、quantization approximation 与 entropy model 放进同一优化目标 ([Ballé et al., 2017](https://pufanyi.com/blog/ml/notes/image-compression#bib-balle2017endtoend))。Scale hyperprior 进一步发送一份较小的 side information，帮助 decoder 预测各 latent 的尺度；side information 自己占 bits，却可能让主 latent 的概率估计更准确、总 rate 更低 ([Ballé et al., 2018](https://pufanyi.com/blog/ml/notes/image-compression#bib-balle2018hyperprior))。这与传统 codec 发送 mode/context 的原则相同：额外信息只有在节省更多主码流时才值得。

JPEG AI 在 2025 年成为首个端到端学习式图像编码国际标准，目标同时覆盖人类观看与机器处理 ([Joint Photographic Experts Group, 2025](https://pufanyi.com/blog/ml/notes/image-compression#bib-jpeg2025aistandard))。这说明 learned codec 已进入标准化阶段，却不意味着现有图片管线已自动迁移：模型复杂度、能耗、硬件加速、确定性、bitstream 互操作和长期 decoder 可得性仍然是部署的一部分。

## 实际选格式时，从约束倒推

可以依次回答：

1. **能否丢信息？** 像素级资产、医学/科学数据或继续编辑的中间件，先考虑 lossless；最终观看副本再评估 lossy。
2. **图像是什么类型？** 照片、截图、文字、透明 UI、像素画、HDR 和噪声丰富的素材需要不同策略。
3. **谁来解码？** 浏览器、App、打印管线、设计软件和归档系统的支持范围，通常比纸面压缩率更先决定答案。
4. **是否需要额外能力？** Alpha、animation、HDR、progressive loading、metadata 与 legacy JPEG reconstruction 都可能改变格式选择。
5. **编码成本是否值得？** 节省的存储与传输，要和 CPU/GPU 时间、能耗、延迟及维护复杂度一起算。

对于普通照片发布，先用目标平台稳定支持的现代 encoder 做真实内容测试，再保留必要 fallback；对于截图和图形，不要默认照片 codec 会更好；对于归档，除了 lossless，还要考虑开放规范、decoder 的长期可得性与校验策略。

## 进入视频压缩前，应该已经会什么

到这里，图片压缩可以浓缩成一条因果链：

$$
\text{samples}
\xrightarrow{\text{prediction / transform}}
\text{集中分布}
\xrightarrow{\text{quantization}}
\text{允许的失真}
\xrightarrow{\text{entropy coding}}
\text{bits}.
$$

继续读视频前，可以先确认自己能回答五个问题：

1. 为什么 residual 元素并没有变少，却可能需要更少 bits？
2. 为什么 RGB→YCbCr 不等于 4:2:0，后者又为什么有损？
3. 为什么 DCT 输出同样多的 coefficients，仍然有助于压缩？
4. 哪一步让 decoder 无法精确恢复原图，entropy coding 又为什么不改变画面？
5. 为什么 encoder 与 decoder 必须使用相同的 prediction 依据？

如果这些问题都能沿着上面的数值例子讲清楚，就可以进入[视频压缩](https://pufanyi.com/blog/ml/notes/video-compression)。视频并不会另起炉灶：它保留 prediction、transform、quantization 与 entropy coding，只把「从同一张图的邻居预测」扩展成「从已经重建的其他帧预测」。新增的核心是 motion compensation、reference dependency、GOP 与跨帧 rate–distortion decision。

## References

Alliance for Open Media. (n.d.). *AV1 Image File Format (AVIF)* (Version 1.0.0). [aomediacodec.github.io](https://aomediacodec.github.io/av1-avif/v1.0.0.html "https://aomediacodec.github.io/av1-avif/v1.0.0.html")

Ballé, J., Laparra, V., & Simoncelli, E. P. (2017). End-to-End Optimized Image Compression. *International Conference on Learning Representations*. [openreview.net](https://openreview.net/forum?id=rJxdQ3jeg "https://openreview.net/forum?id=rJxdQ3jeg")

Ballé, J., Minnen, D., Singh, S., Hwang, S. J., & Johnston, N. (2018). Variational Image Compression with a Scale Hyperprior. *International Conference on Learning Representations*. [openreview.net](https://openreview.net/forum?id=rkcQFMZRb "https://openreview.net/forum?id=rkcQFMZRb")

Google for Developers. (n.d.). *WebP Compression Techniques*. [developers.google.com](https://developers.google.com/speed/webp/docs/compression "https://developers.google.com/speed/webp/docs/compression")

Joint Photographic Experts Group. (2023). *JPEG XL White Paper*. [ds.jpeg.org](https://ds.jpeg.org/whitepapers/jpeg-xl-whitepaper.pdf "https://ds.jpeg.org/whitepapers/jpeg-xl-whitepaper.pdf")

Joint Photographic Experts Group. (2025). *JPEG AI Becomes an International Standard*. [jpeg.org](https://jpeg.org/items/20250219_press.html "https://jpeg.org/items/20250219_press.html")

Joint Photographic Experts Group. (n.d.). *JPEG 1*. [jpeg.org](https://jpeg.org/jpeg/ "https://jpeg.org/jpeg/")

World Wide Web Consortium. (2025). *Portable Network Graphics (PNG) Specification (Third Edition)*. [w3.org](https://www.w3.org/TR/png-3/ "https://www.w3.org/TR/png-3/")
