什么是图像二值化?¶
图像二值化是将图像中的像素点根据阈值分为两类(通常是黑色和白色),使图像仅保留黑白两种颜色的处理过程。例如,一张照片经过二值化后,可能只剩下“文字”和“背景”的黑白对比,这种简化能极大降低后续图像分析的复杂度,常用于文字识别、形状检测等场景。
为什么需要二值化?¶
- 简化图像:去除中间灰度,只保留黑白信息,减少计算量。
- 突出特征:让目标区域(如文字、物体轮廓)与背景形成强烈对比,便于后续处理(如边缘检测、形状识别)。
准备工作:安装与导入库¶
首先确保已安装OpenCV和NumPy库:
pip install opencv-python numpy
导入所需库:
import cv2
import numpy as np
核心步骤:图像二值化的实现¶
二值化处理的核心是cv2.threshold()函数,语法如下:
ret, thresh = cv2.threshold(gray, thresh_value, max_value, threshold_type)
gray:输入图像(必须是灰度图)。thresh_value:手动设定的阈值(0-255)。max_value:超过阈值后像素的赋值(通常为255,即白色)。threshold_type:阈值类型(如二值化、反二值化等)。- 返回值:
ret为实际使用的阈值,thresh为处理后的二值化图像。
常用阈值类型及效果¶
threshold_type参数决定了像素的分类规则,常见类型如下:
1. cv2.THRESH_BINARY:
像素值 > 阈值 → 白色(255);否则 → 黑色(0)。
公式:thresh = 255 if pixel > thresh_value else 0
-
cv2.THRESH_BINARY_INV:
像素值 > 阈值 → 黑色(0);否则 → 白色(255)。
公式:thresh = 0 if pixel > thresh_value else 255 -
cv2.THRESH_OTSU:
自动计算最优阈值(无需手动设定thresh_value),适用于背景与目标亮度差异大的图像。需与其他类型结合使用(如THRESH_BINARY + THRESH_OTSU)。
代码实战:从图像读取到二值化¶
以一张简单的灰度图为例(若没有图像,可用手机拍摄一张黑白对比明显的图片,如硬币、文字等):
# 1. 读取图像并转为灰度图
img = cv2.imread("test.jpg") # 替换为你的图像路径(如"coin.jpg")
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) # 转为灰度图(OpenCV默认读取BGR格式)
# 2. 手动阈值二值化(阈值设为127)
ret, thresh_binary = cv2.threshold(
gray,
thresh_value=127, # 手动阈值(可根据图像调整)
max_value=255,
threshold_type=cv2.THRESH_BINARY # 二值化类型
)
# 3. Otsu自动阈值二值化(无需手动设阈值)
ret_otsu, thresh_otsu = cv2.threshold(
gray,
thresh_value=0, # 设为0时,Otsu自动计算阈值
max_value=255,
threshold_type=cv2.THRESH_BINARY + cv2.THRESH_OTSU # 结合Otsu算法
)
# 4. 显示结果(用matplotlib更直观)
import matplotlib.pyplot as plt
plt.figure(figsize=(12, 4))
plt.subplot(131), plt.imshow(cv2.cvtColor(img, cv2.COLOR_BGR2RGB)), plt.title("原图")
plt.subplot(132), plt.imshow(thresh_binary, cmap="gray"), plt.title("手动阈值(127)")
plt.subplot(133), plt.imshow(thresh_otsu, cmap="gray"), plt.title("Otsu自动阈值")
plt.show()
关键细节:阈值的选择¶
- 手动阈值:若图像亮度均匀,可尝试
thresh_value=127(默认中间值),但需根据图像调整(如暗图像可能设为50,亮图像设为200)。 - Otsu自动阈值:无需手动调参,适合背景与目标对比度高的场景(如文字、证件照)。
扩展:自适应阈值(处理光照不均)¶
若图像中不同区域亮度差异大(如光照不均的照片),全局阈值效果差,需用自适应阈值:
thresh_adaptive = cv2.adaptiveThreshold(
gray,
max_value=255,
adaptive_method=cv2.ADAPTIVE_THRESH_MEAN_C, # 邻域均值作为阈值
threshold_type=cv2.THRESH_BINARY,
block_size=11, # 邻域大小(必须为奇数,如11、15)
C=2 # 邻域均值减去2作为最终阈值
)
总结¶
图像二值化是图像处理的基础操作,通过cv2.threshold()可快速实现。关键步骤是:
1. 读取图像并转灰度;
2. 选择阈值类型(手动/Otsu/自适应);
3. 应用二值化并显示结果。
掌握二值化后,可进一步用于边缘检测、文字识别、目标分割等更复杂的计算机视觉任务。
课后练习:尝试用不同阈值类型处理同一张图像,观察效果差异;用Otsu方法处理一张光照不均的照片,对比手动阈值的结果。