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

03篇--二值化与自适应二值化

二值化

定义

何为二值化?顾名思义,就是将图像中的像素值改为只有两种值,黑与白。此为二值化。

二值化操作的图像只能是灰度图,意思就是二值化也是一个二维数组,它与灰度图都属于单信道,仅能表示一种色调。而二值化表示的是 极致的黑 与 极致的白。

如何设置二值化

1.阈值法(THRESH_BINARY)

通过设置一个阈值,将灰度图中的每一个像素值与该阈值进行比较,小于等于阈值的像素就被设置为0(黑),大于阈值的像素就被设置为maxval(白)。        

原理代码如下: 

import cv2
import numpy as np# 读取彩色图
img = cv2.imread("./flower.png")# 先转换成灰度图
img_gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)img_binary = np.zeros_like(img_gray)# 设置一个阈值
thresh = 127# 遍历灰度图的每一个像素点
for i in range(img_gray.shape[0]):for j in range(img_gray.shape[1]):if img_gray[i][j] <= thresh:img_binary[i, j] = 0else:img_binary[i, j] = 255cv2.imshow('image', img)
cv2.imshow('image_gray', img_gray)
cv2.imshow('image_binary', img_binary)
cv2.waitKey(0)

效果如下:

 

 2.反阈值法(THRESH_BINARY_INV)

与阈值法相反。反阈值法是当灰度图的像素值大于阈值时,该像素值将会变成0(黑),当灰度图的像素值小于等于阈值时,该像素值将会变成maxval(白)。

原理代码:

跟上面阈值法的代码一样,只是把 >= 换成 <= ,将筛选对象调换即可

 

将阈值法与反阈值法的处理结果对比,可以发现,两者的黑白色调刚好相反

3.截断阈值法(THRESH_TRUNC):

指将灰度图中的所有像素与阈值进行比较,像素值大于阈值的部分将会被修改为阈值,小于等于阈值的部分不变。换句话说,经过截断阈值法处理过的二值化图中的最大像素值就是阈值。

4.低阈值零处理(THRESH_TOZERO)

就是像素值小于等于阈值的部分被置为0(也就是黑色),大于阈值的部分不变。

5.超阈值零处理(THRESH_TOZERO_INV)

就是将灰度图中的每个像素与阈值进行比较,像素值大于阈值的部分置为0(也就是黑色),像素值小于等于阈值的部分不变。

6.OTSU阈值法(THRESH_OTSU)

在介绍OTSU阈值法之前,我们首先要了解一下双峰图片的概念。

双峰图片就是指灰度图的直方图上有两个峰值,直方图就是对灰度图中每个像素值的点的个数的统计图,如下图所示。

OTSU算法是通过一个值将这张图分前景色和背景色(也就是灰度图中小于这个值的是一类,大于这个值的是一类),通过统计学方法(最大类间方差)来验证该值的合理性,当根据该值进行分割时,使用最大类间方差计算得到的值最大时,该值就是二值化算法中所需要的阈值。通常该值是从灰度图中的最小值加1开始进行迭代计算,直到灰度图中的最大像素值减1,然后把得到的最大类间方差值进行比较,来得到二值化的阈值。具体实现过程,我们不用考虑,直接调用即可。

threshold函数

上述方法只是介绍其原理,在opencv库中这些方法都已经被封装好了,我们只需要调用这些接口即可,并不需要我们手动实现。通过threshold函数来调用,具体介绍如下:

功能:用于对图像进行二值化处理

参数:

  • src: 输入图像,这应该是一个灰度图像(即单通道图像)。如果你有一个彩色图像,你需要先使用 cv2.cvtColor() 将其转换为灰度图。
  • thresh: 阈值,用于将像素划分为两部分。这个值是一个浮点数或整数,取决于图像的数据类型。
  • maxVal: 最大值,用于设置高于阈值的像素值。这个值通常是一个整数,表示你想要将高于阈值的像素设置为的具体数值。
  • type: 阈值类型,这是一个标志,用于指定如何应用阈值。OpenCV 提供了几种不同的阈值类型,如 cv2.THRESH_BINARY、cv2.THRESH_BINARY_INV、cv2.THRESH_TRUNC、cv2.THRESH_TOZERO 和 cv2.THRESH_TOZERO_INV。
  • dst: 输出图像,与输入图像具有相同的大小和类型。这是一个可选参数,如果不提供,函数会创建一个新的图像来存储二值化结果。(一般不会设置这个参数)

函数返回值:

  • ret: 实际使用的阈值。在某些情况下(如使用 cv2.THRESH_OTSU 或 cv2.THRESH_TRIANGLE 标志时),这个值可能会与输入的 thresh 不同。(因为这两个算法会自动计算阈值,从而覆盖掉你所设置的阈值)
  • dst: 二值化后的图像。

代码示例

import cv2# 读取彩色图
img = cv2.imread("./flower.png")# 先转换成灰度图
img_gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)# 调用cv2的二值化函数
ret, img_binary = cv2.threshold(img_gray, 200, 255, cv2.THRESH_BINARY + cv2.THRESH_OTSU)
print(ret)      # 使用的阈值,可能不是你设定的阈值cv2.imshow('image', img)
cv2.imshow('image_gray', img_gray)
cv2.imshow('image_binary', img_binary)
cv2.waitKey(0)

自动化二值化

与二值化算法相比,自适应二值化更加适合用在明暗分布不均的图片,因为图片的明暗不均,导致图片上的每一小部分都要使用不同的阈值进行二值化处理,这时候传统的二值化算法就无法满足我们的需求了,于是就出现了自适应二值化。

adaptiveThreshold函数

自适应二值化方法会对图像中的所有像素点计算其各自的阈值,这样能够更好的保留图片里的一些信息。通过adaptiveThreshold函数调用

功能:对图像应用自适应阈值处理。

参数:

  • src: 输入图像,必须为灰度图像。
  • maxValue: 超过或等于阈值的像素值被赋予的值。它可以是任意数值,但通常设置为 255(表示白色)。
  • adaptiveMethod: 自适应阈值算法的选择。有两种选择:
    • cv2.ADAPTIVE_THRESH_MEAN_C:计算邻域的平均值,然后从平均值中减去常数 C。
    • cv2.ADAPTIVE_THRESH_GAUSSIAN_C:计算邻域像素的加权和(使用高斯窗口),然后从加权和中减去常数 C。
  • thresholdType: 阈值类型,与固定阈值函数 cv2.threshold() 相同。通常是 cv2.THRESH_BINARY 或 cv2.THRESH_BINARY_INV。
  • blockSize: 用于计算阈值的邻域大小(必须是奇数)也就是
  • C: 从计算出的平均值或加权和中减去的常数。
import cv2# 读取彩色图
img = cv2.imread("./lena.png")# 先转换成灰度图
img_gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)# 调用自适应二值化函数
img_adaptive = cv2.adaptiveThreshold(img_gray,   # 参数1 灰度图255,    # 参数2 最大值cv2.ADAPTIVE_THRESH_GAUSSIAN_C, # 参数3 自适应方法cv2.THRESH_BINARY,  # 参数4 二值化类型7,  # 参数5 核的大小5   # 参数6 计算的阈值减去这个常数是最终阈值)
cv2.imshow('image', img)
cv2.imshow('image_gray', img_gray)
cv2.imshow('image_adaptive_binary', img_adaptive)
cv2.waitKey(0)

http://www.lryc.cn/news/502532.html

相关文章:

  • 基于python的一个简单的压力测试(DDoS)脚本
  • 基于 Spring Boot 实现图片的服务器本地存储及前端回显
  • 深入 TCP VJ-Style
  • go高性能单机缓存项目
  • 数据结构绪论
  • 前端开发常用四大框架学习难度咋样?
  • OWASP 十大安全漏洞的原理
  • 论文 | ChunkRAG: Novel LLM-Chunk Filtering Method for RAG Systems
  • ORACLE SQL思路: 多行数据有相同字段就合并成一条数据 分页展示
  • SpringBoot 手动实现动态切换数据源 DynamicSource (中)
  • y3编辑器教学5:触发器2 案例演示
  • 数值分析——插值法(二)
  • 杨振宁大学物理视频中黄色的字,c#写程序去掉
  • uni-app 设置缓存过期时间【跨端开发系列】
  • 微信小程序base64图片与临时路径互相转换
  • 蓝桥杯刷题——day2
  • 5.删除链表的倒数第N个节点
  • 自己总结:selenium高阶知识
  • 前端怎么预览pdf
  • activemq 的安装部署
  • 【H3CNE邓方鸣】配置链路聚合+2024.12.11
  • C语言 学习 日志 递归函数 2024/12/12
  • 【Ubuntu】使用ip link工具创建虚拟局域网并配置?
  • flink sink kafka的事务提交现象猜想
  • 网络原理03
  • 每天40分玩转Django:简介和环境搭建
  • 【蓝桥杯最新板】蓝桥杯嵌入式液晶上实现电子时钟
  • 【机器学习】基础知识:拟合度(Goodness of Fit)
  • 使用Jackson库在Java应用程序中将Map对象转换为JSON数组字符串,以及反向操作
  • 深入解析强化学习中的 Generalized Advantage Estimation (GAE)