Datawhale_计算机视觉基础_图像处理(6)——图像分割/二值化及opencv实现

图像阈值化分割是一种传统的最常用的图像分割方法,因其实现简单、计算量小、性能较稳定而成为图像分割中最基本和应用最广泛的分割技术。它特别适用于目标和背景占据不同灰度级范围的图像。它不仅可以极大的压缩数据量,而且也大大简化了分析和处理步骤,因此在很多情况下,是进行图像分析、特征提取与模式识别之前的必要的图像预处理过程。

一、算法理论介绍

1.1 最大类间方差法(大津阈值法)

大津法(OTSU)是一种确定图像二值化分割阈值的算法,由日本学者大津于1979年提出。从大津法的原理上来讲,该方法又称作最大类间方差法,因为按照大津法求得的阈值进行图像二值化分割后,前景与背景图像的类间方差最大。

它被认为是图像分割中阈值选取的最佳算法:
计算简单,不受图像亮度和对比度的影响,因此在数字图像处理上得到了广泛的应用。它是按图像的灰度特性,将图像分成背景和前景两部分。因方差是灰度分布均匀性的一种度量, 背景和前景之间的类间方差越大,说明构成图像的两部分的差别越大,当部分前景错分为背景或部分背景错分为前景都会导致两部分差别变小。因此,使类间方差最大的分割意味着错分概率最小。
  • 应用: 是求图像全局阈值的最佳方法,应用不言而喻,适用于大部分需要求图像全局阈值的场合。
  • 优点: 计算简单快速,不受图像亮度和对比度的影响。
  • 缺点: 对图像噪声敏感;只能针对单一目标分割;当目标和背景大小比例悬殊、类间方差函数可能呈现双峰或者多峰,这个时候效果不好。

1.2 自适应阈值

前面介绍了OTSU算法,但这算法属于全局阈值法,所以对于某些光照不均的图像,这种全局阈值分割的方法会显得苍白无力(这个可以见下图)

在这里插入图片描述

这种办法就是自适应阈值法(adaptiveThreshold),它的思想不是计算全局图像的阈值,而是根据图像不同区域亮度分布,计算其局部阈值,所以对于图像不同区域,能够自适应计算不同的阈值,因此被称为自适应阈值法。(其实就是局部阈值法)

如何确定局部阈值呢?可以计算某个邻域(局部)的均值、中值、高斯加权平均(高斯滤波)来确定阈值。值得说明的是:如果用局部的均值作为局部的阈值,就是常说的移动平均法。

二、opencv实现

2.1 最大类间方差法

cv2.threshold(
    src:表示的是图片源
    thresh:表示的是阈值(起始值)
    maxval:表示的是最大值
    type:表示的是这里划分的时候使用的是什么类型的算法,常用值为0(cv2.THRESH_BINARY)

        THRESH_BINARY 将一个灰色的图片,变成要么是白色要么就是黑色
)
# 超过100 的设置为255
temp = cv2.threshold(img, thresh = 100, maxval = 255, type=cv2.THRESH_BINARY)
# thresh = temp[0]
# pic_deal = temp[1]
temp_dark = cv2.threshold(img_dark, thresh = 100, maxval = 255, type=cv2.THRESH_BINARY)

# cv2.imshow("original", img)
# cv2.imshow("original_dark", img_dark)
# cv2.imshow("THRESH_BINARY", temp[1])
# cv2.imshow("THRESH_BINARY_dark", temp_dark[1])
# cv2.waitKey(0)

fig, axes = plt.subplots(2, 2 , figsize=(15,15))
axes[0, 0].imshow(img)
axes[0, 0].set_title('original')
axes[0, 1].imshow(img_dark)
axes[0, 1].set_title('original_dark')
axes[1, 0].imshow(temp[1])
axes[1, 0].set_title('THRESH_BINARY')
axes[1, 1].imshow(temp_dark[1])
axes[1, 1].set_title('THRESH_BINARY_dark')
plt.show()

在这里插入图片描述

2.2 自适应阈值

自适应的时候需要用灰度图片

  • 图片转灰度
img =  cv2.imread(pic_fil, cv2.IMREAD_UNCHANGED) 
img_dark =  cv2.imread(pic_fil_dark, cv2.IMREAD_UNCHANGED) 
img = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
img_dark = cv2.cvtColor(img_dark, cv2.COLOR_BGR2GRAY)

cv2.adaptiveThreshold(
img  输入图像. 
maxValue,
adaptiveMethod 
    ADAPTIVE_THRESH_MEAN_C:小区域内取均值
    ADAPTIVE_THRESH_GAUSSIAN_C:小区域内加权求和,权重是个高斯核

thresholdType = CV_THRESH_BINARY,cv2.THRESH_BINARY_INV
block_size , 小区域的面积 如11就是11*11的小块
C 最终阈值等于小区域计算出的阈值再减去此值

)
temp = cv2.adaptiveThreshold(img, maxValue=255
                         ,adaptiveMethod = cv2.ADAPTIVE_THRESH_GAUSSIAN_C
                         ,thresholdType = cv2.THRESH_BINARY
                         ,block_size = 11
                         ,C = 5
                         )


temp_dark = cv2.adaptiveThreshold(img_dark, maxValue=255
                         ,adaptiveMethod = cv2.ADAPTIVE_THRESH_GAUSSIAN_C
                         ,thresholdType = cv2.THRESH_BINARY
                         ,block_size = 11
                         ,C = 5
                         )


fig, axes = plt.subplots(2, 2 , figsize=(15,15))
axes[0, 0].imshow(img, cmap='gray')
axes[0, 0].set_title('original')
axes[0, 1].imshow(img_dark, cmap='gray')
axes[0, 1].set_title('original_dark')
axes[1, 0].imshow(temp, cmap='gray')
axes[1, 0].set_title('GAUSSIAN——THRESH_BINARY')
axes[1, 1].imshow(temp_dark, cmap='gray')
axes[1, 1].set_title('GAUSSIAN——THRESH_BINARY_dark')
plt.show()

在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Scc_hy

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值