OpenCV 将彩色图像转换为单通道灰度图像 cv2.cvtColor
OpenCV 将彩色图像转换为单通道灰度图像 cv2.cvtColor
flyfish
使用 cv2.cvtColor 函数将读取到的彩色帧图像 frame 转换为灰度图像 gray。cv2.cvtColor 函数用于颜色空间转换,第一个参数是输入图像,第二个参数是颜色转换代码,cv2.COLOR_BGR2GRAY 表示从 BGR 颜色空间转换为灰度颜色空间。
import cv2
video_path = 'input_video.mp4'
cap = cv2.VideoCapture(video_path)
while True:ret, frame = cap.read()gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY) # 转灰度# 后续处理(如检测轮廓)cv2.imshow('Gray Frame', gray)if cv2.waitKey(1) == ord('q'):break
cap.release()
cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
这行代码的作用是将一个 BGR 颜色空间的图像转换为灰度图像
颜色空间的概念
在计算机中,图像是由像素点构成的,每个像素点可以用不同的颜色模型来表示其颜色信息。BGR(Blue, Green, Red)是一种常见的颜色模型,在 OpenCV 里,图像默认采用 BGR 颜色空间,也就是每个像素点由蓝、绿、红三个通道的数值来确定颜色,每个通道的取值范围通常是 0 - 255。
而灰度图像则是指每个像素只有一个数值来表示其亮度,数值范围同样是 0 - 255,0 代表黑色,255 代表白色。
转换原理
把 BGR 图像转换为灰度图像的核心原理是按照特定的权重对 BGR 三个通道的数值进行加权平均,这是因为人眼对不同颜色光的敏感度有所不同,其中对绿色光最为敏感,对蓝色光最不敏感。所以在转换时,绿色通道的权重最大,蓝色通道的权重最小。
转换公式如下:
[
Gray = 0.299 \times R + 0.587 \times G + 0.114 \times B
]
其中, R R R、 G G G、 B B B 分别代表红、绿、蓝三个通道的像素值, G r a y Gray Gray 是转换后的灰度值。
代码示例
下面是一个简单的 Python 代码示例,用于手动实现 cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
的功能:
import cv2
import numpy as np# 读取图像
image = cv2.imread('example.jpg')# 手动实现 BGR 转灰度
height, width, _ = image.shape
gray_manual = np.zeros((height, width), dtype=np.uint8)for i in range(height):for j in range(width):b, g, r = image[i, j]gray_value = int(0.299 * r + 0.587 * g + 0.114 * b)gray_manual[i, j] = gray_value# 使用 cv2.cvtColor 进行转换
gray_cv2 = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)# 显示结果
cv2.imshow('Manual Gray', gray_manual)
cv2.imshow('CV2 Gray', gray_cv2)
cv2.waitKey(0)
cv2.destroyAllWindows()
人眼对颜色感知差异的基本原理
不同颜色的光在人眼中会产生不同的亮度感知,绿色最容易被人眼感知,其次是红色,蓝色最不易被感知。所以在将彩色图像转换为灰度图像时,需要对不同颜色通道赋予不同的权重,以更准确地反映人眼所看到的亮度。
不同权重公式的来源
1. 灰度值 = 0.114 × 蓝色 + 0.587 × 绿色 + 0.299 × 红色 \text{灰度值} = 0.114 \times \text{蓝色} + 0.587 \times \text{绿色} + 0.299 \times \text{红色} 灰度值=0.114×蓝色+0.587×绿色+0.299×红色
这个公式是基于 ITU-R BT.601 标准(以前称为 CCIR 601),该标准主要用于标清电视(SDTV)。它是经过大量实验和研究得出的,适用于处理标准清晰度的视频和图像,在早期的图像和视频处理中广泛使用。
2. 灰度值 = 0.07 × 蓝色 + 0.72 × 绿色 + 0.21 × 红色 \text{灰度值} = 0.07 \times \text{蓝色} + 0.72 \times \text{绿色} + 0.21 \times \text{红色} 灰度值=0.07×蓝色+0.72×绿色+0.21×红色
这个公式来源于 ITU-R BT.709 标准,该标准是为高清电视(HDTV)制定的。随着显示技术的发展,高清电视的普及使得人们需要更适合高清图像和视频的颜色转换公式。BT.709 标准考虑了高清显示设备的特性以及人眼对高清图像中颜色的感知,因此权重分配和 BT.601 有所不同。
实际应用中的选择
在实际应用中,选择使用哪个公式取决于具体的场景和数据来源:
- 标清内容处理:如果处理的是旧的标清视频、图像,或者数据是基于标清标准采集的,那么使用 BT.601 标准的公式更为合适。
- 高清内容处理:对于高清视频、图像,如现代的数字电影、高清电视节目等,使用 BT.709 标准的公式能得到更符合人眼视觉感受的灰度图像。