Python图像处理之膨胀与腐蚀的操作


Posted in Python onFebruary 07, 2021

引言

膨胀与腐蚀是图像处理中两种最基本的形态学操作,膨胀将目标点融合到背景中,向外部扩展,腐蚀与膨胀意义相反,消除连通的边界,使边界向内收缩。在本文中我们将了解使用内核的图像膨胀与腐蚀的基本原理。

让我们开始吧,同样我们需要导入必需的库。

import numpy as np
import matplotlib.pyplot as plt
from skimage.io import imread, imshow
from skimage.draw import circle
from skimage.morphology import erosion, dilation

首先让我们创建一个容易操作的形状--一个简单的圆。

circ_image = np.zeros((100, 100))
circ_image[circle(50, 50, 25)] = 1
imshow(circ_image);

Python图像处理之膨胀与腐蚀的操作

现在让我们定义一个内核。

cross = np.array([[0,1,0],
   [1,1,1],
   [0,1,0]])
imshow(cross, cmap = 'gray');

Python图像处理之膨胀与腐蚀的操作

将腐蚀函数应用到创建的圆上。

eroded_circle = erosion(circ_image, cross)
imshow(eroded_circle);

Python图像处理之膨胀与腐蚀的操作

图像看起来几乎一模一样。要看到那些微小的差异,我们必须仔细查看图像。

linecolor = 'red'
fig, ax = plt.subplots(1, 2, figsize=(12, 5))
ax[0].imshow(circ_image, cmap = 'gray');
ax[0].set_title('Original', fontsize = 19)
ax[0].axvline(x = 25, color = linecolor)
ax[0].axvline(x = 75, color = linecolor)
ax[0].axhline(y = 25, color = linecolor)
ax[0].axhline(y = 75, color = linecolor)
ax[1].imshow(eroded_circle, cmap = 'gray');
ax[1].set_title('Eroded', fontsize = 19)
ax[1].axvline(x = 25, color = linecolor)
ax[1].axvline(x = 75, color = linecolor)
ax[1].axhline(y = 25, color = linecolor)
ax[1].axhline(y = 75, color = linecolor)
fig.tight_layout()

Python图像处理之膨胀与腐蚀的操作

我们可以看到,被腐蚀的圆已经略微缩小了。这就是腐蚀一个对象的意义。如果我们对腐蚀函数进行迭代,它的效果会变得非常明显。

def multi_erosion(image, kernel, iterations):
 for i in range(iterations):
 image = erosion(image, kernel)
 return image
ites = [2,4,6,8,10,12,14,16,18,20]
fig, ax = plt.subplots(2, 5, figsize=(17, 5))
for n, ax in enumerate(ax.flatten()):
 ax.set_title(f'Iterations : {ites[n]}', fontsize = 16)
 new_circle = multi_erosion(circ_image, cross, ites[n])
 ax.imshow(new_circle, cmap = 'gray');
 ax.axis('off')
fig.tight_layout()

Python图像处理之膨胀与腐蚀的操作

上图清楚地显示了图像是如何被腐蚀的。现在让我们尝试改变内核,如果我们使用水平线和垂直线内核代替交叉内核会怎样呢?

h_line = np.array([[0,0,0],
   [1,1,1],
   [0,0,0]])
v_line = np.array([[0,1,0],
   [0,1,0],
   [0,1,0]])
fig, ax = plt.subplots(1, 2, figsize=(15, 5))
ax[0].imshow(h_line, cmap='gray');
ax[1].imshow(v_line, cmap='gray');
fig.tight_layout()

Python图像处理之膨胀与腐蚀的操作

ites = [2,4,6,8,10,12,14,16,18,20]
fig, ax = plt.subplots(2, 5, figsize=(17, 5))
for n, ax in enumerate(ax.flatten()):
 ax.set_title(f'Horizontal Iterations : {ites[n]}', fontsize = 12)
 new_circle = multi_erosion(circ_image, h_line, ites[n])
 ax.imshow(new_circle, cmap = 'gray');
 ax.axis('off')
fig.tight_layout()
fig, ax = plt.subplots(2, 5, figsize=(17, 5))
for n, ax in enumerate(ax.flatten()):
 ax.set_title(f'Vertical Iterationss : {ites[n]}', fontsize = 12)
 new_circle = multi_erosion(circ_image, v_line, ites[n])
 ax.imshow(new_circle, cmap = 'gray');
 ax.axis('off')
fig.tight_layout()

Python图像处理之膨胀与腐蚀的操作

正如我们所看到的,水平和垂直的腐蚀以不同的方式影响着图像。使用水平内核我们得到一个垂直方向细长的圆;而使用垂直内核我们得到一个水平方向细长的圆。

你可能会奇怪,为什么使用垂直内核,会得到一个水平方向细长的圆呢?

因为腐蚀函数是分别寻找垂直和水平的线条,并慢慢把它们削掉。膨胀函数将会让我们更清晰的理解这一点。

使用下面的函数设置处理的图像、膨胀内核以及迭代次数。

def multi_dilation(image, kernel, iterations):
 for i in range(iterations):
 image = dilation(image, kernel)
 return image

让我们看一下处理后的图像有什么不同。

dilated_circle = multi_dilation(circ_image, cross, 1)
linecolor = 'red'
fig, ax = plt.subplots(1, 2, figsize=(12, 5))
ax[0].imshow(circ_image, cmap = 'gray');
ax[0].set_title('Original', fontsize = 19)
ax[0].axvline(x = 25, color = linecolor)
ax[0].axvline(x = 75, color = linecolor)
ax[0].axhline(y = 25, color = linecolor)
ax[0].axhline(y = 75, color = linecolor)
ax[1].imshow(dilated_circle, cmap = 'gray');
ax[1].set_title('Dilated', fontsize = 19)
ax[1].axvline(x = 25, color = linecolor)
ax[1].axvline(x = 75, color = linecolor)
ax[1].axhline(y = 25, color = linecolor)
ax[1].axhline(y = 75, color = linecolor)
fig.tight_layout()

Python图像处理之膨胀与腐蚀的操作

可以清楚地看到圆现在已经越过了红线,这清楚地表明它已经扩大了。现在让我们对水平和垂直扩张进行迭代。

ites = [2,4,6,8,10,12,14,16,18,20]
fig, ax = plt.subplots(2, 5, figsize=(17, 5))
for n, ax in enumerate(ax.flatten()):
 ax.set_title(f'Horizontal Iterations : {ites[n]}', fontsize = 
   12)
 new_circle = multi_dilation(circ_image, h_line, ites[n])
 ax.imshow(new_circle, cmap = 'gray');
 ax.axis('off')
fig.tight_layout()
fig, ax = plt.subplots(2, 5, figsize=(17, 5))
for n, ax in enumerate(ax.flatten()):
 ax.set_title(f'Vertical Iterationss : {ites[n]}', fontsize = 12)
 new_circle = multi_dilation(circ_image, v_line, ites[n])
 ax.imshow(new_circle, cmap = 'gray');
 ax.axis('off')
fig.tight_layout()

Python图像处理之膨胀与腐蚀的操作

现在可以非常清楚地看到,水平扩张增加了图像宽度,而垂直扩张增加了图像高度。

现在我们已经了解了膨胀与腐蚀的基本原理,下面来看一个相对复杂的图像。

complex_image = imread('complex_image.png')
imshow(complex_image);

Python图像处理之膨胀与腐蚀的操作

在上面的图像中,我们看到了水平线、垂直线和圆的混合物。我们可以使用膨胀和腐蚀函数孤立地观察每一种形状。

为了得到圆,我们可以先腐蚀垂直的线,再腐蚀水平的线。但要记住最后要对图像进行膨胀,因为腐蚀函数同样腐蚀了圆。

step_1 = multi_erosion(complex_image, h_line,3)
step_2 = multi_erosion(step_1, v_line,3)
step_3 = multi_dilation(step_2, h_line,3)
step_4 = multi_dilation(step_3, v_line,3)
steps = [step_1, step_2, step_3, step_4]
names = ['Step 1', 'Step 2', 'Step 3', 'Step 4']
fig, ax = plt.subplots(2, 2, figsize=(10, 10))
for n, ax in enumerate(ax.flatten()):
 ax.set_title(f'{names[n]}', fontsize = 22)
 ax.imshow(steps[n], cmap = 'gray');
 ax.axis('off')
fig.tight_layout()

Python图像处理之膨胀与腐蚀的操作

同样,下面的代码将得到水平的线。

step_1 = multi_erosion(complex_image, cross, 20)
step_2 = multi_dilation(step_1, h_line, 20)
step_3 = multi_dilation(step_2, v_line,2)
steps = [step_1, step_2, step_3]
names = ['Step 1', 'Step 2', 'Step 3']
fig, ax = plt.subplots(1, 3, figsize=(10, 10))
for n, ax in enumerate(ax.flatten()):
 ax.set_title(f'{names[n]}', fontsize = 22)
 ax.imshow(steps[n], cmap = 'gray');
 ax.axis('off')
fig.tight_layout()

Python图像处理之膨胀与腐蚀的操作

为了得到垂直的线,我们可以创建一个新的内核。

long_v_line = np.array([[0,1,0],
   [0,1,0],
   [0,1,0],
   [0,1,0],
   [0,1,0]])
step_1 = multi_erosion(complex_image, long_v_line, 10)
step_2 = multi_dilation(step_1 ,long_v_line, 10)
steps = [step_1, step_2]
names = ['Step 1', 'Step 2']
fig, ax = plt.subplots(1, 2, figsize=(10, 10))
for n, ax in enumerate(ax.flatten()):
 ax.set_title(f'{names[n]}', fontsize = 22)
 ax.imshow(steps[n], cmap = 'gray');
 ax.axis('off')
fig.tight_layout()

Python图像处理之膨胀与腐蚀的操作

注意,内核并不局限于本文中提到的这几种,可以根据不同的需求自己定义合适的内核。

总结

内核腐蚀和膨胀是图像处理领域需要理解的基本概念。它们甚至可能是任何图像处理模块的第一课。直观地理解它们将是你以后在这个领域成功的关键。

到此这篇关于Python图像处理之膨胀与腐蚀的操作的文章就介绍到这了,更多相关Python图像膨胀与腐蚀内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Python 相关文章推荐
videocapture库制作python视频高速传输程序
Dec 23 Python
Python入门之三角函数atan2()函数详解
Nov 08 Python
Python编程求质数实例代码
Jan 31 Python
pycharm+PyQt5+python最新开发环境配置(踩坑)
Feb 11 Python
详解Python函数式编程—高阶函数
Mar 29 Python
python字符串中匹配数字的正则表达式
Jul 03 Python
Python3操作MongoDB增册改查等方法详解
Feb 10 Python
解决ROC曲线画出来只有一个点的问题
Feb 28 Python
Python加载数据的5种不同方式(收藏)
Nov 13 Python
python 爬虫爬取京东ps4售卖情况
Dec 18 Python
Python机器学习工具scikit-learn的使用笔记
Jan 28 Python
Python图像处理之图像拼接
Apr 28 Python
django inspectdb 操作已有数据库数据的使用步骤
Feb 07 #Python
python数据抓取3种方法总结
Feb 07 #Python
python 批量将中文名转换为拼音
Feb 07 #Python
如何用用Python将地址标记在地图上
Feb 07 #Python
python 三种方法提取pdf中的图片
Feb 07 #Python
Python 转移文件至云对象存储的方法
Feb 07 #Python
Python调用SMTP服务自动发送Email的实现步骤
Feb 07 #Python
You might like
thinkphp实现发送邮件密码找回功能实例
2014/12/01 PHP
CentOS6.5 编译安装lnmp环境
2014/12/21 PHP
php数组合并与拆分实例分析
2015/06/12 PHP
PHP模拟asp.net的StringBuilder类实现方法
2015/08/08 PHP
YII动态模型(动态表名)支持分析
2016/03/29 PHP
ThinkPHP3.1.x修改成功与失败跳转页面的方法
2017/09/29 PHP
Nigma vs AM BO3 第二场2.13
2021/03/10 DOTA
jQuery 源码分析笔记(2) 变量列表
2011/05/28 Javascript
jQuery 获取/设置/删除DOM元素的属性以a元素为例
2014/05/23 Javascript
node.js正则表达式获取网页中所有链接的代码实例
2014/06/03 Javascript
javascript制作坦克大战全纪录(1)
2014/11/27 Javascript
swtich/if...else的替代语句
2015/08/16 Javascript
JavaScript中使用数组方法汇总
2016/02/16 Javascript
基于jQuery实现收缩展开功能
2016/03/18 Javascript
利用jQuery+localStorage实现一个简易的计时器示例代码
2017/12/25 jQuery
让webpack+vue-cil项目不再自动打开浏览器的方法
2018/09/27 Javascript
vue发送ajax请求详解
2018/10/09 Javascript
小程序实现页面顶部选项卡效果
2018/11/06 Javascript
jQuery实现全选、反选和不选功能的方法详解
2019/12/04 jQuery
微信小程序中的上拉、下拉菜单功能
2020/03/13 Javascript
解决antd日期选择组件,添加value就无法点击下一年和下一月问题
2020/10/29 Javascript
[00:31]DOTA2上海特级锦标赛 Fnatic战队宣传片
2016/03/04 DOTA
Python正则简单实例分析
2017/03/21 Python
Python实现获取命令行输出结果的方法
2017/06/10 Python
python 分离文件名和路径以及分离文件名和后缀的方法
2018/10/21 Python
Python 通过requests实现腾讯新闻抓取爬虫的方法
2019/02/22 Python
Django Rest framework频率原理与限制
2019/07/26 Python
python MD5加密的示例
2020/10/19 Python
Python模块常用四种安装方式
2020/10/20 Python
使用CSS3的rem属性制作响应式页面布局的要点解析
2016/05/24 HTML / CSS
HTML5 表单验证失败的提示语问题
2017/07/13 HTML / CSS
你常见到的runtime exception
2016/09/05 面试题
营销与策划个人求职信
2013/09/22 职场文书
学生打架检讨书1000字
2014/01/16 职场文书
市场营销毕业求职信
2014/08/07 职场文书
Nginx源码编译安装过程记录
2021/11/17 Servers