当前位置: 首页 > web >正文

OpenCV阈值处理完全指南:从基础到高级应用

引言

阈值处理是图像处理中最基础、最常用的技术之一,它能够将灰度图像转换为二值图像,为后续的图像分析和处理奠定基础。本文将全面介绍OpenCV中的各种阈值处理方法,包括原理讲解、代码实现和实际应用场景。

一、什么是阈值处理?

阈值处理(Thresholding)是通过设定一个或多个阈值,将图像的像素值分为若干类的过程。对于灰度图像,通常是选择一个阈值,将像素分为"黑"和"白"两类,从而创建二值图像。

数学表达式:

dst(x,y) = maxVal if src(x,y) > thresh= 0      otherwise

二、OpenCV中的阈值处理函数

OpenCV提供了cv2.threshold()函数用于基本的阈值处理,其函数原型为:

retval, dst = cv2.threshold(src, thresh, maxval, type[, dst])

参数说明:

  • src:输入图像(必须为灰度图)
  • thresh:阈值
  • maxval:当像素值超过阈值时赋予的最大值
  • type:阈值类型
  • retval:实际使用的阈值(某些方法会自动计算)
  • dst:输出图像

三、5种基本阈值处理方法

1. 二进制阈值化(THRESH_BINARY)

import cv2
import numpy as npimg = cv2.imread('image.jpg', 0)  # 以灰度模式读取
ret, thresh1 = cv2.threshold(img, 127, 255, cv2.THRESH_BINARY)

效果:像素值>127设为255,否则设为0

2. 反二进制阈值化(THRESH_BINARY_INV)

ret, thresh2 = cv2.threshold(img, 127, 255, cv2.THRESH_BINARY_INV)

效果:与THRESH_BINARY相反

3. 截断阈值化(THRESH_TRUNC)

ret, thresh3 = cv2.threshold(img, 127, 255, cv2.THRESH_TRUNC)

效果:像素值>127设为127,否则保持不变

4. 阈值化为0(THRESH_TOZERO)

ret, thresh4 = cv2.threshold(img, 127, 255, cv2.THRESH_TOZERO)

效果:像素值>127保持不变,否则设为0

5. 反阈值化为0(THRESH_TOZERO_INV)

ret, thresh5 = cv2.threshold(img, 127, 255, cv2.THRESH_TOZERO_INV)

效果:与THRESH_TOZERO相反

四、自适应阈值处理

当图像光照不均时,全局阈值效果不佳,此时可以使用自适应阈值:

thresh = cv2.adaptiveThreshold(img, 255, cv2.ADAPTIVE_THRESH_MEAN_C,cv2.THRESH_BINARY, 11, 2)

参数说明:

  • adaptiveMethod:自适应方法
    • ADAPTIVE_THRESH_MEAN_C:邻域均值
    • ADAPTIVE_THRESH_GAUSSIAN_C:邻域加权和(高斯)
  • blockSize:邻域大小(奇数)
  • C:从均值或加权和中减去的常数

五、Otsu’s二值化(大津算法)

对于双峰图像(直方图有两个明显峰值),Otsu方法可以自动确定最佳阈值:

ret2, th2 = cv2.threshold(img, 0, 255, cv2.THRESH_BINARY+cv2.THRESH_OTSU)

六、实际应用案例

1. 文档扫描与OCR预处理

def preprocess_for_ocr(image_path):img = cv2.imread(image_path, 0)# 使用Otsu方法自动阈值化_, thresh = cv2.threshold(img, 0, 255, cv2.THRESH_BINARY_INV + cv2.THRESH_OTSU)# 去噪kernel = np.ones((3,3), np.uint8)processed = cv2.morphologyEx(thresh, cv2.MORPH_OPEN, kernel, iterations=1)return processed

2. 工业检测中的缺陷识别

def detect_defects(reference_img, test_img):# 转换为灰度图ref_gray = cv2.cvtColor(reference_img, cv2.COLOR_BGR2GRAY)test_gray = cv2.cvtColor(test_img, cv2.COLOR_BGR2GRAY)# 计算差异diff = cv2.absdiff(ref_gray, test_gray)# 自适应阈值处理thresh = cv2.adaptiveThreshold(diff, 255, cv2.ADAPTIVE_THRESH_GAUSSIAN_C,cv2.THRESH_BINARY, 11, 2)# 寻找轮廓contours, _ = cv2.findContours(thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)# 绘制缺陷区域result = test_img.copy()for cnt in contours:if cv2.contourArea(cnt) > 10:  # 忽略小面积x,y,w,h = cv2.boundingRect(cnt)cv2.rectangle(result, (x,y), (x+w,y+h), (0,0,255), 2)return result

七、阈值处理的高级技巧

1. 多阈值处理

def multi_threshold(image):gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)# 定义三个阈值_, th1 = cv2.threshold(gray, 50, 255, cv2.THRESH_BINARY)_, th2 = cv2.threshold(gray, 100, 255, cv2.THRESH_BINARY)_, th3 = cv2.threshold(gray, 150, 255, cv2.THRESH_BINARY)# 组合结果result = np.zeros_like(gray)result[(gray >= 0) & (gray < 50)] = 0result[(gray >= 50) & (gray < 100)] = 100result[(gray >= 100) & (gray < 150)] = 200result[gray >= 150] = 255return result

2. 基于HSV空间的阈值处理

def hsv_threshold(image):hsv = cv2.cvtColor(image, cv2.COLOR_BGR2HSV)# 定义颜色范围(示例:红色)lower_red = np.array([0, 120, 70])upper_red = np.array([10, 255, 255])mask1 = cv2.inRange(hsv, lower_red, upper_red)lower_red = np.array([170, 120, 70])upper_red = np.array([180, 255, 255])mask2 = cv2.inRange(hsv, lower_red, upper_red)# 合并maskmask = mask1 + mask2# 应用maskresult = cv2.bitwise_and(image, image, mask=mask)return result

八、性能优化

性能优化建议:

  1. 对小图像使用全局阈值,对大图像使用自适应阈值
  2. 在循环中处理视频帧时,预先转换为灰度图
  3. 合理选择blockSize(通常11-31之间的奇数)

九、总结

阈值处理是图像分割和特征提取的基础,掌握各种阈值处理方法能够为更复杂的计算机视觉任务打下坚实基础。本文介绍了OpenCV中的基本阈值处理方法、自适应阈值和大津算法,并提供了实际应用案例和高级技巧。希望通过本文的学习,您能够根据不同的应用场景选择合适的阈值处理方法。

http://www.xdnf.cn/news/6676.html

相关文章:

  • 5G行业专网部署费用详解:投资回报如何最大化?
  • Zephyr OS Nordic芯片的Flash 操作
  • 提权脚本Powerup命令备忘单
  • 从小区到商场再到校园,AI智能分析网关V4高空抛物检测方案全场景护航
  • Spring Boot 封装 MinIO 工具
  • DDS(数据分发服务) 和 P2P(点对点网络) 的详细对比
  • [QMT量化交易小白入门]-五十四、核心资产ETF轮动目前年化只有74%了,在过滤掉当天止损,当天买入的之后
  • Java 21 + Spring Boot 3.5:AI驱动的高性能框架实战
  • require/exports 或 import/export的联系和区别,各自的使用场景
  • 基于Rust语言的Rocket框架和Sqlx库开发WebAPI项目记录(二)
  • Expo项目在本地打包apk的问题
  • Vue主题色切换实现方案(CSS 变量 + 类名切换)
  • 【前端】[vue3] [uni-app]使用 vantUI 框架
  • 使用 OpenCV 将图像中标记特定颜色区域
  • 黑马k8s(九)
  • day 26
  • Python训练营打卡 Day27
  • Java 中使用 Redis 实现消息订阅/发布
  • 三极管知识
  • 根据台账批量制作个人表
  • 5G-A和未来6G技术下的操作系统与移动设备变革:云端化与轻量化的发展趋势
  • 【Pandas】pandas DataFrame kurt
  • 如何让 Google 收录 Github Pages 个人博客
  • go封装将所有数字类型转浮点型,可设置保留几位小数
  • AG-UI 协议:重构多模态交互,开启智能应用新纪元
  • C42-作业练习
  • 光谱相机的空间分辨率和时间分辨率
  • MinIO 开源的分布式文件服务器
  • 三格电子上新了——IO-Link系列集线器
  • 【C++】 —— 笔试刷题day_29