像素格式有哪些?
摄像头常见输出可分为未压缩像素格式和视频编码格式。YUV、RGB 是存储色彩的像素数据,而 H.264 则用来压缩编码这些数据。
- 未压缩像素格式 (Uncompressed Pixel Formats):这类格式可直接描述图像的亮度、色度或 RGB 分量。本文中的 YUYV、NV12 等属于这一类;严格来说,传感器输出的 Bayer 数据才通常称为 RAW。未压缩格式又主要分为两种:
| 格式大类 | 代表格式 | 内存占用 (1080p每帧) | 主要优缺点 | 数据排列方式 |
|---|---|---|---|---|
| RGB类 | RGB24, BGR24, RGBA32 | ~6.2MB | 数据量大,逻辑直观,适合直接在屏幕上显示和处理。 | 每个像素固定存储红、绿、蓝三原色的数据。 |
| YUV类 | YUYV, NV12, I420, YV12 | 约3~4.1MB | 将亮度和颜色分离,利于压缩和兼容黑白显示;数据量通常小于 RGB。 | 每个像素都有亮度(Y)值,而色度(U/V)值则由相邻像素共享。 |
YUV的采样方式(如4:4:4、4:2:2、4:2:0)决定了色度信息的保留程度。常见YUV格式的区别如下:
| 格式名称 | 采样方式 | 存储类型 | 特点 |
|---|---|---|---|
| YUYV | 4:2:2 | 打包 (Packed) | 每两个像素共享一对UV,顺序交错排列。 |
| UYVY | 4:2:2 | 打包 (Packed) | 与YUYV类似,但顺序变为U、Y、V、Y。 |
| NV12 | 4:2:0 | 半平面 (Semi-Planar) | 一个Y平面,一个UV交错存储的平面,在Windows、Android和硬件编解码中很常见。 |
| I420 | 4:2:0 | 平面 (Planar) | 三个平面顺序存储:全部Y,然后全部U,最后全部V。在FFmpeg等软件中广泛使用。 |
| YV12 | 4:2:0 | 平面 (Planar) | 与I420类似,但存储顺序是Y,然后V,最后U。 |
| NV16 | 4:2:2 | 半平面 (Semi-Planar) | 一个 Y 平面,后接 UV 交错平面;相比 NV12 保留更多垂直方向的色度信息。 |
- 视频编码格式 (Video Codecs):
- 特点:通过复杂的算法(如帧内、帧间预测)对原始像素数据进行高倍率压缩。
- 代表:H.264、H.265、MJPEG等。它们是处理视频文件或通过网络传输时的格式。其中,H.264 是一种高效的视频编码标准,常与原始像素格式(如YUYV)搭配使用,先将数据压缩成H.264再传输。
🔬 YUYV 的深层解读与数据帧结构
1. YUYV 为什么重要?
YUYV 在摄像头和视频领域扮演着“通用语言”的角色。它数据量适中(YUV 4:2:2采样),能提供不错的图像质量,因此被很多USB摄像头(遵循UVC标准)默认支持。
2. YUYV 的数据帧长什么样?
YUYV是一种打包(Packed)格式,意味着它的Y、U、V分量是交错存储在一起的。
采样方式与数据组成:
- 采样方式:YUV 4:2:2,意味着在水平方向上,每2个像素点共享一对UV色度信息,但每个像素都保留自己独立的Y亮度信息。
- 数据组成:一个像素对 (4字节) =
Y0 (1字节) + U (1字节) + Y1 (1字节) + V (1字节)。所以,如果图像分辨率是W x H,那么一帧完整画面的数据量约为W \* H \* 2字节。
3. 数据排列顺序
假设你有一张4x4像素的图片,YUYV数据在内存中的排列顺序如下图所示,一个格子代表1个字节:
| 字节偏移 | Byte 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 |
|---|---|---|---|---|---|---|---|---|
| 数据内容 | Y00 | U00 | Y01 | V00 | Y02 | U01 | Y03 | V01 |
| 所属像素 | 像素(0,0) | (0,0)&(0,1) | 像素(0,1) | (0,0)&(0,1) | 像素(0,2) | (0,2)&(0,3) | 像素(0,3) | (0,2)&(0,3) |
Y后面跟行号和列号,例如Y00表示第0行第0列的Y值。- 可以看到,U和V分量总是被相邻的两个Y像素所共享。
🆚 与其他像素格式的数据帧对比
YUYV与其他常见格式的主要区别在于采样方式和排列方式。
| 对比项 | YUYV (YUV 4:2:2, Packed) | NV12 (YUV 4:2:0, Semi-Planar) | RGB24 (RGB, Packed) | H.264 (压缩格式) |
|---|---|---|---|---|
| 采样方式 | YUV 4:2:2 | YUV 4:2:0 | N/A (每个像素包含完整R,G,B) | 基于视频编码标准 |
| 存储类型 | 打包 (Packed) | 半平面 (Semi-Planar) | 打包 (Packed) | 码流格式 (Bitstream) |
| 数据排列 | 交错排列:Y U Y V | 先存全部Y,再存交错UV | 顺序排列:R G B 或 B G R | 包含NAL单元等复杂结构 |
| 每像素占用 | 16 bits = 2 bytes | 12 bits = 1.5 bytes | 24 bits = 3 bytes | 高度可变,通常远小于原始格式 |
| 内存布局示例 | [Y0 U0 Y1 V0] [Y2 U1 Y3 V1] | [Y0 Y1 Y2 Y3 ...] [U0 V0 U1 V1 ...] | [R0 G0 B0] [R1 G1 B1] [R2 G2 B2] ... | 无法直接查看像素,需要解码器解析 |
| 优点 | 图像质量较好,兼容性好 | 压缩率高,是流媒体和硬件编解码的主流格式 | 色彩表现直接、完整 | 压缩率极高,适合网络传输和存储 |
| 缺点 | 数据量较大 | 垂直方向的色彩细节有损失 | 数据量巨大 | 编解码复杂,有算力开销 |
💡 YUYV 与 H.264 的本质区别
最后,澄清一个最核心的误解:YUYV 和 H.264 是完全不同层次的概念,它们是“原材料”与“压缩包”的关系。
- YUYV:未压缩像素格式(原材料)。它可直接用来描述图像的亮度和色度。
- H.264:视频编码标准(压缩算法/压缩包)。为了高效存储或通过网络传输,用H.264算法对“原材料”(如YUYV数据)进行复杂压缩,得到的数据流就是H.264格式。
整个过程通常是:CMOS传感器捕获光信号 → 经 ISP 处理并转换成 YUYV 等未压缩格式数据 → 送入编码器(如 H.264 编码器)进行压缩 → 输出 H.264 格式的码流。选择格式,本质是在“画质好、体积大”的未压缩数据和“体积小、但编解码有开销”的压缩数据间做权衡。
摄像头实际返回的数据格式与选择
V4L2 设备返回的是驱动当前协商出的格式:有些摄像头直接输出未压缩的 YUYV、YVYU、NV12 或 NV16;有些则由摄像头内部 ISP / 编码器先压缩,再输出 MJPEG、H.264 或 H.265 码流。应通过 VIDIOC_ENUM_FMT 和 VIDIOC_S_FMT 确认、设置实际格式,不能只凭摄像头型号推断。
| 返回格式 | 性质 | 典型特点与适用场景 |
|---|---|---|
| YUYV / YVYU | 未压缩 YUV 4:2:2,打包存储 | 延迟低、兼容性好,但带宽和存储开销较大;适合实时采集、图像处理。 |
| NV12 | 未压缩 YUV 4:2:0,半平面存储 | 每像素约 1.5 字节,适合许多硬件编解码器;色度细节低于 4:2:2。 |
| NV16 | 未压缩 YUV 4:2:2,半平面存储 | 每像素约 2 字节,色度信息多于 NV12,适合更重视色彩细节的处理链路。 |
| MJPEG | 帧内压缩码流 | 每帧都是独立 JPEG,体积适中、解码简单,随机取帧方便。 |
| H.264 / H.265 | 帧内和帧间压缩码流 | 压缩率高,适合网络传输和长期存储;解码有算力需求,帧间编码也会带来缓存和延迟。 |
- 追求低延迟、并且主机有足够 USB/内存带宽时,优先考虑 YUYV、NV12 等未压缩格式。
- 希望在画质、带宽和实现复杂度间折中时,可选择 MJPEG。
- 带宽受限,或用于网络传输、录像存储时,优先考虑 H.264/H.265;应用需使用相应解码器获取像素数据。