目录:
- 1.了解膨胀腐蚀的基本原理
- 2.练习实现图像的膨胀腐蚀操作
- 3.练习实现图像的开操作和闭操作
- 4.练习实现图像的顶帽和黑帽操作
形态学转换
定义
形态学通常表示生物学的一个分支,该分支主要研究动植物的形态和结构。在图像中我们使用形态学表示数学形态学的内容,将数学形态学作为工具从图像中提取表达和描绘区域形状的有用图像分量,如边界,骨架和凸壳。
数学形态学的语言是集合论。形态学为大量的图像处理问题提供一种一致且有利的方法。数学形态学中的集合表示图像中的对象,例如,在二值图像中,所有白色像素的集合是该图像的一个完整的形态学描述。
数学形态学是由一组形态学的代数运算子组成的,它的基本运算有4个: 膨胀(或扩张)、腐蚀(或侵蚀)、开启和闭合,它们在二值图像和灰度图像中各有特点。基于这些基本运算还可推导和组合成各种数学形态学实用算法,用它们可以进行图像形状和结构的分析及处理,包括图像分割、特征抽取、边缘检测、 图像滤波、图像增强和恢复等。
原理
形态学操作是根据图像形状进行的简单操作。一般情况下对二值化图像进行的操作。需要输入两个参数,一个是原始图像,第二个被称为结构化元素或核,它是用来决定操作的性质的。两个基本的形态学操作是腐蚀和膨胀。他们的变体构成了开运算,闭运算,梯度等。
一、腐蚀和膨胀
1.腐蚀
就像土壤侵蚀一样,这个操作会把前景物体的边界腐蚀掉(但是前景仍然是白色)。这是怎么做到的呢?卷积核沿着图像滑动,如果与卷积核对应的原图像的所有像素值都是 1*,那么中心元素就保持原来的像素值,否则就变为零*。
这会产生什么影响呢?根据卷积核的大小靠近前景的所有像素都会被腐蚀掉(变为 0),所以前景物体会变小,整幅图像的白色区域会减少。这对于去除白噪声很有用,也可以用来断开两个连在一块的物体等。
代码示例:
# -*- coding:utf-8 -*-
import cv2
import numpy as np
img = cv2.imread("img.jpg")
#构造一个5*5的卷积核
kernel = np.ones((5,5),np.uint8)
erosion = cv2.erode(img,kernel,iterations = 1)
cv2.imshow("img",img)
cv2.imshow("erosion",erosion)
原图 腐蚀:
注释:
从原图可以看出来,图像的边缘有一圈黑色的轮廓,当进行腐蚀操作时,卷积核移动到轮廓附近时,当核内所有值为一样时,保持原像素值,当存在不一样的时候(卷积核一般在轮廓中,一半在后景图像上),腐蚀操作就将不一样的转换为与轮廓一样的值,所以黑色轮廓面积扩大了,看起来就像被腐蚀了一样。
2、膨胀
与腐蚀相反,与卷积核对应的原图像的像素值中只要有一个是 1,中心元素的像素值就是 1。所以这个操作会增加图像中的白色区域(前景)。一般在去噪声时先用腐蚀再用膨胀。因为腐蚀在去掉白噪声的同时,也会使前景对象变小。所以我们再对他进行膨胀。这时噪声已经被去除了,不会再回来了,但是前景还在并会增加。膨胀也可以用来连接两个分开的物体。
代码示例:
# -*- coding:utf-8 -*-
import cv2
import numpy as np
img = cv2.imread("img.jpg")
#构造一个5*5的卷积核
kernel = np.ones((5,5),np.uint8)
dilation = cv2.dilate(img,kernel,iterations = 1)
cv2.imshow("img",img)
cv2.imshow("dilation",dilation)
原图:膨胀:
注释:
从原图可以看出来,图像的边缘有一圈黑色的轮廓,当进行膨胀操作时,卷积核移动到轮廓附近时,当核内值有一个为1时,便将中心像素的值设为1。当卷积核位于图像边缘时,卷积核内也可能存在为1的值,卷积核中心便设为1,图像由此便扩展了一圈,看起来就像图像膨胀了。
必须熟悉膨胀和腐蚀的操作原理,以下所有操作都是以膨胀和腐蚀为基础进行的二次操作。
二、开操作(开运算)和闭操作(闭运算)
1.开操作
先进行腐蚀再进行膨胀就叫做开操作。它被用来去除噪声。由于噪声点也是有轮廓的,所以可以先使用腐蚀,将噪声点去除,再进行膨胀,将图像“还原”。
代码示例:
mport cv2
import numpy as np
#构造了一个含有噪声的图片
img = cv2.imread("noise.jpg")
#构造5*5卷积核
kernel = np.ones((5,5),np.uint8)
#开操作,先进性腐蚀,再进行膨胀
opening = cv2.morphologyEx(img, cv2.MORPH_OPEN, kernel)
cv2.imshow("img",img)
cv2.imshow("opening",opening)
原图:开操作:
2.闭操作
先膨胀再腐蚀。它经常被用来填充前景物体中的小洞,或者前景物体上的小黑点。
代码示例:
# -*- coding:utf-8 -*-
import cv2
import numpy as np
img = cv2.imread("img.jpg")
kernel = np.ones((5,5),np.uint8)
closing = cv2.morphologyEx(img,cv2.MORPH_CLOSE,kernel)
cv2.imshow("img",img)
cv2.imshow("closing",closing)
原图:闭操作:
由效果图可以看出来,闭操作将图像中的一些小一点的噪声点去除了,可以设置大一点的卷积核,这样就可以去除更多更大的噪声点。
三、顶帽和黑帽
0、形态学梯度
其实就是一幅图像膨胀与腐蚀的差别。结果看上去就像前景物体的轮廓。
代码示例:
# -*- coding:utf-8 -*-
import cv2
import numpy as np
img = cv2.imread("img.jpg")
kernel = np.ones((5,5),np.uint8)
gradient = cv2.morphologyEx(img, cv2.MORPH_GRADIENT, kernel)
cv2.imshow("img",img)
cv2.imshow("gradient",gradient)
原图:形态学梯度:
1、顶帽
顶帽又称礼帽,结果为原图和开运算的结果图之差。
d
s
t
=
s
r
c
−
o
p
e
n
(
s
r
c
,
e
l
e
m
e
n
t
)
dst = src - open(src,element)
dst=src−open(src,element)
因为开运算到来的结果是放大了裂痕或者局部低亮度的区域,因此,从原图中减去运算后的图,得到的效果图突出了比原图轮廓周围的区域更明亮的区域,且这一操作和选择的核的大小相关。顶帽运算往往用来分离比邻近点亮一些的斑块。当一幅图像具有大幅的背景的时候,而微小物品比较有规律的情况下,可以使用顶帽运算进行背景提取。
代码示例:
# -*- coding:utf-8 -*-
import cv2
import numpy as np
img = cv2.imread("img.jpg")
kernel = np.ones((9,9),np.uint8)
tophat = cv2.morphologyEx(img, cv2.MORPH_TOPHAT, kernel)
cv2.imshow("img",img)
cv2.imshow("tophat",tophat)
原图:顶帽:
2、黑帽
黑帽运算,闭运算的结果图和原图之差。突出原图像中比周围暗的区域。
d
s
t
=
c
l
o
s
e
(
s
r
c
,
e
l
e
m
e
n
t
)
−
s
r
c
dst = close(src,element) - src
dst=close(src,element)−src
代码示例:
# -*- coding:utf-8 -*-
import cv2
import numpy as np
img = cv2.imread("img.jpg")
kernel = np.ones((9,9),np.uint8)
blackhat = cv2.morphologyEx(img, cv2.MORPH_BLACKHAT, kernel)
cv2.imshow("img",img)
cv2.imshow("blackhat",blackhat)
原图:黑帽:
个人见解如有考虑不周,敬请指点。
参考:《数字图像处理》第三版
OpenCV-Python 中文教程----段力辉