2. 色彩空间基础:RGB、HSV、Lab 色彩空间介绍

做图像处理这么多年,我越来越觉得:选对色彩空间,项目就成功了一半。尤其是光照校正这个方向,很多人一上来就对着 RGB 猛调,结果越调越乱。

今天咱们就把三种最常用的色彩空间掰开揉碎讲清楚。特别是 HSV,为什么它在光照处理里这么吃香?

2.1 RGB 色彩空间——最熟悉,也最不听话

RGB 就是红绿蓝三通道叠加。显示器、摄像头、手机屏幕,全用这套。每个像素三个值,范围 0-255,组合出 1600 多万种颜色。

听起来很完美对吧?但实际用起来,问题就来了。

RGB 的核心缺陷:三个通道高度耦合。你调亮度,三个通道一起变;你调颜色,亮度也跟着跑。说白了,RGB 把「亮度」和「颜色」搅在一起了。

举个例子。一张照片偏暗,你想提亮。在 RGB 里,你得把 R、G、B 三个值都乘个系数。结果呢?亮度是上去了,但颜色也变了——原本的红色可能变得发白,蓝色变得发紫。

我在项目中遇到过这种情况:用 RGB 做直方图均衡化,处理完的图像颜色完全失真,客户直接打回来重做。后来换成 HSV,一次通过。

特性 RGB HSV Lab
亮度与颜色耦合度 高度耦合 分离 完全分离
光照变化敏感度 非常敏感 不敏感(V 通道) 不敏感(L 通道)
人眼感知一致性 差 中等 好
计算复杂度 低 中 高
工程常用场景 显示、存储 光照校正、目标跟踪 颜色分析、色彩管理

2.2 HSV 色彩空间——光照处理的王牌

HSV 把颜色拆成三个分量:Hue(色调)、Saturation(饱和度)、Value(明度)。

  • H(色调):0°-360°,决定是什么颜色。红色、蓝色、绿色,全在这里。
  • S(饱和度):0-1,决定颜色有多纯。0 是灰色,1 是纯色。
  • V(明度):0-1,决定有多亮。0 是全黑,1 是全亮。

关键来了:V 通道只负责亮度,跟颜色无关。你调整 V 通道,H 和 S 完全不受影响。

为什么会这样?因为 HSV 的设计初衷就是把「颜色是什么」和「颜色有多亮」分开。你想想看,这简直就是为光照校正量身定做的。

我的习惯做法:做光照校正时,先把 RGB 转成 HSV,然后只动 V 通道。直方图均衡化、Gamma 校正、对比度拉伸,全在 V 通道上操作。处理完再转回 RGB 显示。效果稳得很。

我曾经接手过一个项目,需要在不同光照条件下检测交通标志。白天、傍晚、隧道里,光照变化极大。用 RGB 做阈值分割,参数调了三天都搞不定。换成 HSV,只对 H 通道做范围筛选,S 和 V 稍微过滤一下,半天就上线了。

2.3 Lab 色彩空间——人眼级别的颜色感知

Lab 是 CIE 组织搞出来的色彩空间,目标是模拟人眼对颜色的感知方式。

  • L(亮度):0-100,从黑到白。
  • a(绿到红):-128 到 127,负值偏绿,正值偏红。
  • b(蓝到黄):-128 到 127,负值偏蓝,正值偏黄。

Lab 最大的优势是感知均匀。什么意思?就是你在 Lab 空间里移动相同的距离,人眼感受到的颜色变化是差不多的。RGB 和 HSV 都做不到这一点。

但 Lab 也有短板:计算量大,而且 a、b 通道的取值范围没有直观的物理意义。你很难像 HSV 那样直接说「把 H 设在 120° 就是绿色」。

注意:Lab 空间在做颜色迁移、色彩分析时非常强大。但如果你只是做光照校正,HSV 的性价比更高。别为了炫技硬上 Lab,工程上讲究的是「够用就好」。

2.4 为什么 HSV 更适合光照处理?

一句话总结:HSV 把光照信息独立出来了。

在 RGB 里,光照变化会同时影响三个通道。在 HSV 里,光照变化主要影响 V 通道,H 和 S 基本不变。这意味着你可以放心大胆地调整亮度,不用担心颜色跑偏。

我给你们看个实际对比。假设一张图片的某个像素在 RGB 里是 (200, 100, 50)。光照变暗后变成 (100, 50, 25)。你算算,R/G/B 的比例完全变了,颜色肯定变。

但同样的像素在 HSV 里,光照变暗只是 V 值从 0.78 降到 0.39,H 和 S 几乎不变。颜色还是那个颜色。

工程建议:只要你的任务涉及光照变化——不管是校正、增强还是归一化——优先考虑 HSV。这是我在几十个项目里踩坑踩出来的经验。

2.5 三种色彩空间的转换关系

实际工程中,我们经常需要在 RGB、HSV、Lab 之间来回切换。OpenCV 提供了现成的函数,但理解背后的转换逻辑很重要。

RGB → HSV 的核心思路:

  1. 把 RGB 归一化到 0-1 范围。
  2. V = max(R, G, B)
  3. S = (V - min(R, G, B)) / V(如果 V=0,则 S=0)
  4. H 的计算稍微复杂一点,根据哪个通道最大来决定基准角度,再偏移。
import cv2
import numpy as np

# RGB 转 HSV
img_rgb = cv2.imread('example.jpg')
img_hsv = cv2.cvtColor(img_rgb, cv2.COLOR_BGR2HSV)

# 只对 V 通道做直方图均衡化
h, s, v = cv2.split(img_hsv)
v_eq = cv2.equalizeHist(v)
img_hsv_eq = cv2.merge([h, s, v_eq])

# 转回 RGB 显示
img_result = cv2.cvtColor(img_hsv_eq, cv2.COLOR_HSV2BGR)

嗯,这里要注意:OpenCV 的 HSV 范围跟理论值不一样。H 是 0-179,S 和 V 是 0-255。别搞混了,我刚开始用的时候就因为这个踩过坑。

2.6 知识体系总览

下面这张图把三种色彩空间的核心逻辑和适用场景串起来了。你可以把它当作本章的「思维导图」。

色彩空间知识体系图 色彩空间知识体系 RGB 色彩空间 红绿蓝三通道叠加 HSV 色彩空间 色调/饱和度/明度 Lab 色彩空间 亮度/绿红/蓝黄 核心特性对比 亮度与颜色耦合 RGB 高度耦合 / HSV 分离 光照敏感度 HSV/Lab 不敏感 计算复杂度 RGB 低 / Lab 高 工程适用场景 RGB 图像显示、存储 摄像头原始数据 HSV 光照校正、目标跟踪 颜色分割、直方图均衡 Lab 颜色迁移、色彩分析 高精度颜色测量 光照校正推荐:HSV > Lab > RGB HSV 性价比最高,Lab 精度最高,RGB 不推荐直接用于光照处理

2.7 避坑指南

最后分享几个我踩过的坑,希望能帮你省点时间。

坑 1:OpenCV 的 HSV 范围不是标准的 0-360/0-100/0-100。H 是 0-179,S 和 V 是 0-255。做阈值分割时一定要换算清楚。

坑 2:HSV 转 RGB 再转 HSV,会有精度损失。别来回转,尽量在一个色彩空间里完成所有操作。

坑 3:Lab 空间的 L 通道虽然独立,但 a、b 通道的取值范围跟图像内容有关。做归一化时别用固定阈值,用统计值更靠谱。

我曾经在一个项目里,用 HSV 做肤色检测。一开始直接拿标准 HSV 范围去筛,结果亚洲人和欧洲人的肤色完全筛不到一起。后来发现,光照不同导致 V 通道差异太大。解决办法是先把 V 通道归一化到固定范围,再筛 H 和 S。效果立竿见影。

嗯,色彩空间这块就讲这么多。记住一句话:选对色彩空间,比调参更重要。