opencv_python阈值处理

本文探讨了Python下OpenCV的图像阈值处理方法,包括简单阈值、自适应阈值及Otsu's二值化。通过实例代码展示了不同阈值处理方法的应用,适合初学者实践。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

看了好多博客,最终发现得好好研究一个人的博客并去做实验,才能达到最好的学习效果。

https://blog.youkuaiyun.com/on2way/article/details/46812121

参考其博客,并发现一个文档网址:

https://docs.opencv.org/3.2.0/d7/d4d/tutorial_py_thresholding.html

是不错的学习资料

本片博客主要使用python_opencv尝试了三种阈值处理方法,现总结如下,并把自己尝试的代码附上。

 图像的阈值处理(python下opencv使用)

1.简单阈值

简单阈值最为简单,选取一个全局阈值,然后把整幅图像分成非黑即白的二值图像。函数为

cv.threshold(),该函数有四个参数,第一个为原图像,第二个进行分类的阈值,第三个是高于(低于)阈值时所赋予的新值,第四个是一个方法选择参数,常用方法选择参数有:

  • cv2.THRESH_BINARY(黑白二值) 高于阈值的设置为新值,低于阈值的为0
  • cv2.THRESH_BINARY_INV(黑白二值反转) 与上一个反过来
  • cv2.THRESH_TRUNC (得到的图像为多像素值) 高于阈值的全为阈值,低于阈值的不变
  • cv2.THRESH_TOZERO 高于阈值的不变,低于阈值的全为0
  • cv2.THRESH_TOZERO_INV 与上一个反过来

 

  • 相关代码:
import cv2

import numpy as np

from matplotlib import pyplot as plt



img = cv2.imread("D:\\software_my_programming\\relate_to_irisrecog\\CASIA-Iris-Lamp\\001\\L\\S2001L01.jpg")

#读取图像,0为灰度图像,1为彩色图像

ret,thresh1 = cv2.threshold(img,127,255,cv2.THRESH_BINARY)

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

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

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

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



titles = ['img','BINARY','BINARY_INV','TRUNC','TOZERO','TOZERO_INV']

images = [img,thresh1,thresh2,thresh3,thresh4,thresh5]



for i in range(6):

    plt.subplot(2,3,i+1)

    plt.imshow(images[i],'gray')

    plt.title(titles[i])

    plt.xticks([]),plt.yticks([])



plt.show()

2.自适应阈值

自适应阈值看成是一个局部性的阈值,通过规定一个区域大小,比较这个点与区域大小里面像素点的平均值(或者其他特征)的大小关系确定这个像素点是属于黑或者白(如果是二值情况)。使用函数为:cv2.adaptiveThreshold() (仅用于灰度图像)

该函数需要6个参数:

 

  • 第一个原始图像
  • 第二个像素值上限
  • 第三个自适应方法Adaptive Method:
  • — cv2.ADAPTIVE_THRESH_MEAN_C :领域内均值
  • —cv2.ADAPTIVE_THRESH_GAUSSIAN_C :领域内像素点加权和,权 重为一个高斯窗口
  • 第四个值的赋值方法:只有cv2.THRESH_BINARY 和cv2.THRESH_BINARY_INV
  • 第五个Block size:规定领域大小(一个正方形的领域)
  • 第六个常数C,阈值等于均值或者加权值减去这个常数(为0相当于阈值 就是求得领域内均值或者加权值)

这种方法理论上得到的效果更好,相当于在动态自适应的调整属于自己像素点的阈值,而不是整幅图像都用一个阈值。

 

  • 相关代码:
import cv2

import numpy as np

from matplotlib import pyplot as plt



img = cv2.imread("D:\\software_my_programming\

\\relate_to_irisrecog\\CASIA-Iris-Lamp\\001\\L\\S2001L01.jpg",0)

#读取图像,0为灰度图像,1为彩色图像

ret,thresh1 = cv2.threshold(img,127,255,cv2.THRESH_BINARY)

thresh2 = cv2.adaptiveThreshold(img,255,cv2.ADAPTIVE_THRESH_MEAN_C,\

cv2.THRESH_BINARY,11,2)

thresh3 = cv2.adaptiveThreshold(img,255,cv2.ADAPTIVE_THRESH_GAUSSIAN_C,\

cv2.THRESH_BINARY,11,2)





titles = ['img','BINARY','ADAPTIVE_THRESH_MEAN_C','ADAPTIVE_THRESH_GAUSSIAN_C',]

images = [img,thresh1,thresh2,thresh3]



for i in range(4):

    plt.subplot(2,2,i+1)

    plt.imshow(images[i],'gray')

    plt.title(titles[i])

    plt.xticks([]),plt.yticks([])



plt.show()

3.Otsu’s二值化

前面对于阈值的处理上,我们选择的阈值都是127,那么实际情况下,怎么去选择这个127呢?有的图像可能阈值不是127得到的效果更好。那么这里我们需要算法自己去寻找到一个阈值,而Otsu’s就可以自己找到一个认为最好的阈值。并且Otsu’s非常适合于图像灰度直方图具有双峰的情况,他会在双峰之间找到一个值作为阈值,对于非双峰图像,可能并不是很好用。那么经过Otsu’s得到的那个阈值就是函数cv2.threshold的第一个参数了。因为Otsu’s方法会产生一个阈值,那么函数cv2.threshold的的第二个参数(设置阈值)就是0了,并且在cv2.threshold的方法参数中还得加上语句cv2.THRESH_OTSU。那么什么是双峰图像(只能是灰度图像才有),就是图像的灰度统计图中可以明显看出只有两个波峰。

 

  • 相关代码:
import cv2

import numpy as np

from matplotlib import pyplot as plt



img = cv2.imread("D:\\software_my_programming\

\\relate_to_irisrecog\\CASIA-Iris-Lamp\\001\\L\\S2001L01.jpg",0)

#读取图像,0为灰度图像,1为彩色图像

ret1,thresh1 = cv2.threshold(img,127,255,cv2.THRESH_BINARY)

#简单滤波



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

#Ostu滤波



print(ret2)





plt.subplot(221),plt.imshow(img,'gray')

plt.subplot(222),plt.hist(img.ravel(),256)#该方法将矩阵转化为一维

plt.subplot(223),plt.imshow(thresh1,'gray')

plt.subplot(224),plt.imshow(thresh2,'gray')

plt.show()

 

 

 

### 实现Canny边缘检测、形态学操作以及寻找轮廓 要在Python中使用OpenCV实现Canny边缘检测、形态学操作和寻找轮廓的功能,可以通过以下方法完成: #### 导入库 首先需要导入必要的库 `cv2` 和 `numpy` 来支持图像处理功能[^1]。 ```python import cv2 import numpy as np ``` #### 图像预处理 加载图像并将其转换为灰度图以便后续处理。由于彩色图像可能含有噪声或其他干扰因素,因此通常建议先对其进行高斯模糊处理以减少这些影响[^4]。 ```python # 加载原始图片 original_img = cv2.imread("image.jpg") # 转换为灰度图 gray_img = cv2.cvtColor(original_img, cv2.COLOR_BGR2GRAY) # 对灰度图应用高斯模糊 blurred_img = cv2.GaussianBlur(gray_img, (3, 3), 0) ``` #### Canny边缘检测 通过调用 `cv2.Canny()` 方法来进行边缘检测。此函数接收两个主要参数作为高低阈值,用于控制哪些像素被认为是强边或弱边。 ```python edges = cv2.Canny(blurred_img, threshold1=50, threshold2=150) ``` #### 形态学操作 为了增强边缘的效果,在某些情况下可以采用开闭运算等形态学技术进一步优化结果。这里展示了一个简单的梯度计算例子[^4]。 ```python kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (5, 5)) gradient = cv2.morphologyEx(edges, cv2.MORPH_GRADIENT, kernel) ``` #### 查找轮廓 利用 `cv2.findContours()` 函数可以从二值化的边缘图中提取出所有的轮廓信息。注意该函数会改变传入的图像数据副本,所以如果还需要保留原样,则应复制一份给定的数据后再传递进去[^3]。 ```python contours, hierarchy = cv2.findContours(gradient.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE) ``` #### 绘制轮廓 最后一步是在原图上画出找到的所有轮廓线框出来供查看验证之用[^3]。 ```python drawing = original_img.copy() cv2.drawContours(drawing, contours, -1, (0, 255, 0), 2) ``` #### 显示最终效果图 将各个阶段的结果分别显示出来便于观察整个流程的变化情况。 ```python cv2.imshow("Original Image", original_img) cv2.imshow("Gray Scale", gray_img) cv2.imshow("Blurred Image", blurred_img) cv2.imshow("Edges Detected by Canny", edges) cv2.imshow("Morphological Gradient", gradient) cv2.imshow("Detected Contours", drawing) cv2.waitKey(0) cv2.destroyAllWindows() ``` 以上就是完整的基于OpenCVPython实现Canny边缘检测、形态学操作及绘制图形轮廓的过程描述[^1].
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值