---
title: "H.264 到底在压什么，以及你手机上那个 4 分钟的 MOV 该用哪条命令救回来"
description: "把 H.264 编码器拆成三步讲透，再演示 Mac 上怎么用 ffmpeg 和 HandBrake 完成最常见的三个视频转换场景。"
date: "2026-10-08"
type: "writing"
kind: "essay"
tags: ["视频编码", "H.264", "ffmpeg", "HandBrake", "macOS"]
draft: false
---

Mac 上传上来一个 iPhone 拍的视频，4 分钟，2.3 GB，后缀是 .MOV。发给同事被拒收，云盘上传提示文件过大。想压缩，但打开"照片"app 找一圈，只找到一个叫"视频压缩"的按钮，点了之后没反应。

先弄清楚 .MOV 是什么。MOV 是容器，里面装的是视频流和音频流。决定文件大小的是里面装的编解码器，容器后缀只是包的外衣。iPhone 从 XS 之后默认用 H.265 拍，老一点的用 H.264。H.264 就是这篇文章要讲的东西。

## H.264 编码器在做什么

H.264 的思路非常朴素。视频相邻帧之间几乎全是一模一样的东西，只有一小块在动，所以不需要每一帧都完整存，只存变化部分，同时告诉播放器"这里相对上一帧往左挪了 3 个像素"。

一个典型编码器做四件事。

第一步是宏块分割。把 1080p 一帧拆成 16x16 像素的小块，一整帧大概三千多个。每个块独立处理。

第二步是运动估计。拿当前块去和参考帧对比，找一个最匹配的位移量。位移最小时算出残差，也就是两帧之间的差异。运动预测精确到四分之一像素，这一步决定了压缩率的地基。

第三步是块内预测。同一个 16x16 块里，内部还可以再切成 8x8 或 4x4 的小块，因为一个宏块里的物体可能不是齐步走的。天空整体不动，一只鸟从中间飞过。编码器得识别这种局部运动。

第四步是 DCT 变换和量化。残差送进离散余弦变换，把空间域信号转成频率域信号。低频信息（画面里的主体、大范围色块）留得多，高频信息（细节、噪点、纹理）留得少。然后按量化步长（QP）舍入，小的高频值直接归零。这一步是唯一有损的部分，也是最关键的一步。QP 越小，保留的高频越多，画质越好，文件越大。QP 越大反过来。整个压缩里，量化是唯一真正动画质的地方。

最后还有熵编码。H.264 里用 CABAC，是 CAVLC 的升级版，比上一代省 5-10% 空间。

这四步走完，就是一份合规的 H.264 码流。编码器还会决定 GOP 结构，把帧排成 I 帧、P 帧、B 帧的组合。I 帧完整存一帧，P 帧只存和 I 的差异，B 帧双向参考前后帧，编码效率高但播放延迟更高。

## 用 ffmpeg 压一个视频

Mac 上装工具，两条命令搞定。

```bash
brew install ffmpeg
brew install --cask handbrake
```

ffmpeg 是命令行，HandBrake 是 GUI，都是同一批人维护的。GUI 用户走 HandBrake，命令行用户走 ffmpeg。

### 换容器不重编码

如果只是想改个后缀，不想动视频流，一条命令就完事。

```bash
ffmpeg -i input.mkv -c:v copy -c:a copy output.mp4
```

`-c:v copy` 表示视频流直接复制。文件秒完，画质完全不变。但前提是目标容器支持原编解码器。MOV 换成 MP4，通常能无缝过。MKV 换成 AVI，可能会报错。

### 从 iPhone MOV 压成通用 MP4

iPhone 用 HEVC 拍的视频，兼容性最差。老电脑、Windows 版浏览器、很多剪辑软件都读不动。压成 H.264 兼容性最好。

```bash
ffmpeg -i input.mov -c:v libx264 -preset medium -crf 23 -c:a aac -b:a 192k output.mp4
```

`libx264` 是软件编码，速度一般但兼容性最好。`-c:a aac` 是音频也要转，因为 HEVC 视频的音频可能是 HE-AAC 或 ALAC，直接放 mp4 有些平台不认。

### 用 Mac 硬件加速

M 系列芯片有 VideoToolbox 硬件编码器，速度快很多，画质略输软件编码，但差距在 CRF 20 以上时几乎看不出。

```bash
ffmpeg -i input.mov -c:v h264_videotoolbox -b:v 6M -c:a aac output.mp4
```

注意硬件编码不支持 CRF，只能用固定码率 `-b:v`。想调质量只能改这个数。

### HandBrake 走图形界面

不想敲命令的话，HandBrake 里有个"Fast 1080p30"预设，直接选，导出。命令行版本是 `HandBrakeCLI`，同样在 Homebrew 里。

```bash
HandBrakeCLI -i input.mov -o output.mp4 -f mp4 -p "Fast 1080p30" -e 1 -E aac -q:a 20 -B 192
```

## CRF 和 preset

CRF 是码率控制模式，从 0 到 51，数字越小画质越好、文件越大。x264 默认 23，实际用得比较多的区间在 18 到 28。

- 22-24 是日常备份和分享够用的区间
- 18-20 是可以反复剪辑的余量
- 15 以下肉眼已经看不出差别了，但文件翻几倍

`-preset` 控制编码速度。`fast` 快但文件大，`slow` 慢但文件小，同一个 CRF 下，`veryslow` 比 `fast` 大约省 15-20% 的空间。日常用 `medium` 平衡速度和质量。

## 常见坑

第一个是 `-crf` 和 `-b:v` 混用。两个是不同码率控制模式，混用会让 CRF 失效。要么定死码率，要么定死质量，二选一。

第二个是忽略音频 codec。不指定 `-c:a`，ffmpeg 会保留原格式。iPhone 的 mov 里可能是 HE-AAC，mp4 通常是 aac，虽然都是 AAC 家族但不同版本。想稳一点就显式指定 `-c:a aac -b:a 192k`。

第三个是可变帧率。iPhone 录屏、120fps 慢动作、HEVC 视频基本都是 VFR。转码时不指定 `-vsync vfr` 或 `-r 30`，某些播放器会跳帧卡顿。iPhone 视频转码建议加 `-vsync vfr`。

第四个是给剪辑用。有些教程说要先用 ProRes 做代理再转回 H.264。ProRes 体积大得多，但编辑流畅。个人用户压完 CRF 20 的 H.264 直接扔给剪映或 DaVinci 用就够了。

## 什么时候不用 H.264

H.265 压缩率高 30-50%，但编解码专利要交钱，硬件解码发热大，M 系列芯片上播放 H.265 明显比 H.264 热。

AV1 开源，压缩率比 H.265 再好 10-20%，但编码极慢，软件编码基本不可用。硬件解码目前只在少数新芯片上有。

VP9 是 Google 的开源方案，压得比 H.264 好但比 H.265 差，Chrome 原生支持，其他平台要装解码器。

个人用户想压手机视频、发朋友圈、云盘备份，H.264 + CRF 码率控制仍然是最省事的选择。

## 一条可以直接用的命令

想省事的，记下面这条就够。

```bash
ffmpeg -i input.mov \
  -c:v libx264 -preset medium -crf 23 \
  -c:a aac -b:a 192k \
  -vsync vfr \
  output.mp4
```

跑完得到一个体积合理、画质够看、兼容性最好的 H.264 MP4。

H.264 的压缩能力来自运动估计、量化和熵编码这三步。Mac 上压视频只需要一行命令，关键是 CRF 和 preset 怎么选，以及音频 codec 别忘。CRF 23 加 medium preset 是日常用的最佳起点，其他都是在这个基础上做微调。
