【干货】计算机视觉实战系列02——用Python做图像处理

【导读】在当今互联网蓬勃发展的时代,图像处理技术也随着人们的需求不断进步,专知成员Hui计划推出一系列计算机视觉入门实战讲解,参照Jan Erik Solem编写的《Python计算机视觉编程》这本书,以时下最流行的Python语言为工具,对图像处理技术的具体操作进行详细讲述,上一次的内容中已经为大家介绍了PIL python图像处理类库的使用,包括读取图像,转换灰度图像,创建缩略图,裁剪图像区域,调整尺寸和旋转。这一次为大家介绍Matplotlib的使用,包括绘图,绘制点和线,以及图像的轮廓和直方图,代码简洁,通俗易懂,旨在让零基础的读者也可以轻松上手!

【干货】计算机视觉实战系列01——用Python做图像处理

Matplotlib基本的图像操作和处理

Python中有好多工具包应用于图像处理当中,本章作为入门章节,首先来介绍Python中最基本的几个工具包,也希望读者可以在之后自行练习。

▌Matplotlib

Matplotlib 是一个 Python 的 2D绘图库,它以各种硬拷贝格式和跨平台的交互式环境生成出版质量级别的图形。它可以很好地帮助我们处理数学运算,绘制图表,或者在图像上绘制点、直线和曲线,具有比PIL更强大的绘图功能。Matplotlib中的PyLib接口包含很多方便用户创建图像的函数。

▌使用默认的绘图属性绘图

以绘制正弦余弦函数曲线为例,介绍相应的函数

代码如下:

from PIL import Image
from pylab import *

x = np.linspace(-np.pi, np.pi, 256, endpoint=True)
C, S = np.cos(x), np.sin(x)
plt.plot(x, C)
plt.plot(x, S)

show()

numpy.linspace:在指定的间隔内返回均匀间隔的数字。返回num均匀分布的样本,在[start, stop]。这个区间的端点可以任意的被排除在外。第一个参数为序列的起始点,第二个参数为序列的结束点,第三个参数为步长,第四个参数意为:如果是True,则一定包括stop,如果为False,一定不会有stop。

结果如下图所示:

上面的两行plot代码为绘制图像,当然还可以对绘制图像做更加具体的要求,比如:

plt.plot(x,C,color='red',linewidth=2.5,linestyle='-')  
plt.plot(x,S,color='blue',linewidth=2.5,linestyle='-.')  

本文只提供plot的部分使用方法,如果读者想了解更多plot的操作,请参考官方网站:http://matplotlib.org/api/pyplot_api.html#matplotlib.pyplot.plot

除此之外,我们还可以对坐标轴的绘制进行设置,具体代码如下:

import numpy as np
import matplotlib.pyplot as plt

x = np.linspace(-np.pi, np.pi, 256, endpoint=True)
C, S = np.cos(x), np.sin(x)
plt.xlim(x.min() * 1.1, x.max() * 1.1)
plt.xticks([-np.pi, -np.pi / 2, 0, np.pi / 2, np.pi],
           [r'$-\pi$', r'$-\pi/2$', r'$0$', r'$+\pi/2$', r'$+\pi$'])

plt.ylim(C.min() * 1.1, C.max() * 1.1)
plt.yticks([-1, 0, +1],
           [r'$-1$', r'$0$', r'$+1$'])
plt.plot(x, C, color='red', linewidth=2.5, linestyle='-')
plt.plot(x, S, color='blue', linewidth=2.5, linestyle='-.')

plt.show()

输出结果如下:

看到yticks和xticks后面一 串的数字,看到就觉得可能有点不知道写的什么,熟悉LaTex的人觉得我们这种想法的人有点傻。其实就是很简单的字符串,但是是为了方便Latex去解析这段字符串。一般以r开始,中间的字符串用$字符串$包围起来。这里是matplotlib中的有关LaTex的使用介绍:Latex的使用

链接:https://matplotlib.org/users/mathtext.html

在完成了坐标轴的设置后,我们还可以通过Matplotlib设置坐标轴位置,Spines 是连接轴刻度标记的线,而且标明了数据区域的边界。 他们可以被放置在任意位置。直到现在,他们仍是轴的边界。我们将要改变现状,因为我们想要spines 置于中间。因为有四个spine(上下左右),我们将要通过设置颜色(无)丢弃上面和右侧的部分。 进而我们移动下面和左边的线到坐标0(数据空间)。

用法为:

Spine(axes, spine_type, path, **kwargs)axes :包含spine的轴实例。spine_type :指定spine类型的字符串path :用于绘制spine的路径实例。例如:我们调用’right’边的spine的’set_color’方法,并且传入’none’参数,这样,左边框的颜色就变成了无色,而’set_position()’方法则使边框的位置改变,“0”代表中心,依靠这个方法我们就能自己“拼凑”出坐标轴,并且能够把其他边框屏蔽掉。’ax.xaxis.set_ticks_position()’方法则设置了坐标轴数据的位置,括号内为传入的位置信息。

此外,我们还可以通过legend()方法添加图例。

完整的代码为:

import numpy as np
import matplotlib.pyplot as plt

ax = plt.subplot(111)
ax.spines['right'].set_color('none')
ax.spines['top'].set_color('none')
ax.xaxis.set_ticks_position('bottom')
ax.spines['bottom'].set_position(('data', 0))
ax.yaxis.set_ticks_position('left')
ax.spines['left'].set_position(('data', 0))

x = np.linspace(-np.pi, np.pi, 256, endpoint=True)
C, S = np.cos(x), np.sin(x)

plt.plot(x, C, color='red', linewidth=2.5, linestyle='-', label=r'$cos(t)$')
plt.plot(x, S, color='blue', linewidth=2.5, linestyle='-', label=r'$sin(t)$')
plt.legend(loc='upper left', frameon=False)

plt.xlim(x.min() * 1.1, x.max() * 1.1)
plt.xticks([-np.pi, -np.pi / 2, 0, np.pi / 2, np.pi],
           [r'$-\pi$', r'$-\pi/2$', r'$0$', r'$+\pi/2$', r'$+\pi$'])

plt.ylim(C.min() * 1.1, C.max() * 1.1)
plt.yticks([-1, 0, +1],
           [r'$-1$', r'$0$', r'$+1$'])
plt.show()  

输出图像为:

▌绘制点和线

下面,我们来看一下在已绘制的图像上绘制点和线。我们首先用到上一节中绘制的图片“test.jpg”

代码如下:

from PIL import Image
from pylab import *

im = array(Image.open("test.jpg"))
imshow(im)
x = [100, 400, 600, 800]
y = [100, 200, 1000, 1200]
plot(x[:2], y[:2], 'b*')

show()

输出结果如下:

我们看到,我们成功在一张导入的图片上绘制出了两个蓝色的五角星。如果加一行代码:

plot(x,y,linewidth=3.5)

我们就将x,y对应点连接在一起了

结果如下图所示:

那么我们回过头来看一下上面的代码:首先为绘制原始图像,然后再x,y列表中给定点的x坐标,y坐标上绘制出蓝色五角星状标记点,注意,我们取x[:2]意为取x列表元素的第零个和第一个,不包含第二个元素,y列表同理,需要注意的是,x,与y列表的取值数量应该一致,否则,系统会报错。而当我们用plot()方法将各个点相连时,程序会自动将所有的x与y的对应点相连,此时,若x与y列表元素数量不一致,系统同样会报错。

绘图时有很多选项可以控制图像的颜色和样式:

plot(x,y)       #默认为蓝色实线
plot(x,y,’r*’)    #红色星状标记
plot(x,y,’go-’)   #带有圆圈标记的绿线
plot(x,y,’ks-’)   #带有正方形标记的黑色点线

颜色标注:

‘b’ #蓝色
‘g’ #绿色
‘r’ #红色
‘c’ #青色
‘m’ #品红
‘y’ #黄色
‘k’ #黑色
‘w’ #白色

线型格式命令:

‘-’ #实线
‘--’#虚线
‘:’#点线

绘制标记格式命令:

‘.’ #点
‘o’ #圆圈
‘s’ #正方形
‘*’ #星形
‘+’ #加号
‘x’ #叉号

▌图像的轮廓和直方图

绘制图像的轮廓(或者其它二位函数的等轮廓线)在工作中非常有用,因为绘制轮廓需要对每个坐标[x,y]的像素值施加一个相同的阈值,所以首先需要将图像灰度化

完整代码如下:

from PIL import Image
from pylab import *

image = array(Image.open('test.jpg').convert('L'))
figure()  # 新建一个图像
gray()  # 不使用颜色信息
contour(image, origin='image')

axis('equal')
plt.show()

显示图像如图所示:

这样我们就成功生成了一张图片的轮廓了。

其中contour()本应用于设置等高线,用法为:

contour(Z) :绘制矩阵Z的等高线 contour(Z,n) :设置等高线的根数(画出来有n根等高线) contour(Z,v) :v是元素随下标单调递增的一维向量,用来设置等高线的值。即在固定的几个值的位置设置等高线。

其中的origin可以传入’upper’,’lower’,’None’,以及’image’等参数用于固定图像的位置。

图像的直方图用来表征该图像的像素值分布情况,用一定数目的小区间(bin)来表征像素值的范围,每个小区间会得到落入该小区域间表示范围的像素数目,该灰度图像的直方图可以使用hist()函数绘制,完整代码如下:

from PIL import Image
from pylab import *

fig = plt.figure(figsize=(15, 15))
image = array(Image.open('test.jpg').convert('L'))

plt.subplot(2, 1, 1)
plt.imshow(image, cmap=cm.gray)
plt.axis("off")
plt.subplot(2, 1, 2)
plt.hist(image.flatten(), 256)  # flatten可以将矩阵转化成一维序列
plt.show()

显示图像如图所示:

hist()函数的第二个参数指定小区间的数目,需要注意的是,因为hist()只接受一维数组作为输入,所以我们在绘制图像直方图之前,必须先对图像进行平压处理,flatten()方法将任意数组按照行优先准则转换成一维数组。

plt.subplot()意为创建子图像。其中括号内传入了三个参数,第一个表示Y轴方向的子图个数,第二个表示X轴方向的子图个数,第三个则表示当前要画图的焦点。

参考文献:

python计算机视觉编程:http://yongyuan.name/pcvwithpython/

-END-

本文分享自微信公众号 - 专知(Quan_Zhuanzhi)

原文出处及转载信息见文内详细说明,如有侵权,请联系 yunjia_community@tencent.com 删除。

原始发表时间:2018-03-13

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏数说工作室

class 类—老司机的必修课 | 统计师的Python日记 第11课

本文是【统计师的Python日记】第11天的日记 回顾一下: 第1天学习了Python的基本页面、操作,以及几种主要的容器类型。 第2天学习了python的函...

393100
来自专栏机器学习算法与Python学习

Python: numpy总结(3)

21、dot矩阵点积 例子: ll = [[1,2,3],[4,5,6],[7,8,9]]ld = dot(ll,ll) print 'dot:',l...

35240
来自专栏数说工作室

家养爬虫的Python技术 | 资料总结

之前有一个讨论: 文本分析怎么整? 文本分析,一个很重要的环节就是网络的数据爬取。爬虫是获取数据的一个重要手段,很多时候我们没有精力也没有资金去采集专业的数...

445110
来自专栏机器学习算法与Python学习

Python:爬虫系列笔记(2) -- 基本了解及urllib的使用

1.什么是爬虫 爬虫,即网络爬虫,大家可以理解为在网络上爬行的一直蜘蛛,互联网就比作一张大网,而爬虫便是在这张网上爬来爬去的蜘蛛咯,如果它遇到资源,那么它就会抓...

37360
来自专栏机器学习算法与Python学习

Python:numpy总结(4)

31、chr函数,获取指定的字符 例子: #获取指定的字符for i in range(65,70): print str(chr(i))...

41990
来自专栏机器学习算法与Python学习

Python:爬虫系列笔记(3) -- urllib库的高级用法

1.设置Headers 有些网站不会同意程序直接用上面的方式进行访问,如果识别有问题,那么站点根本不会响应,所以为了完全模拟浏览器的工作,我们需要设置一些Hea...

42070
来自专栏机器学习算法与Python学习

Python: numpy总结(2)

11、xrange 例子: for i in xrange(3): print i test=[1,2,3,4] print test...

35250
来自专栏机器学习算法与Python学习

Python:set集合、深浅拷贝与函数

1、Set基本数据类型 a、set集合,是一个无序且不重复的元素集合 class set(object): """ set() -> new empty ...

37960
来自专栏机器学习算法与Python学习

Python:理解GC机制非常重要!!!

引用计数 Python默认的垃圾收集机制是“引用计数”,每个对象维护了一个ob_ref字段。它的优点是机制简单,当新的引用指向该对象时,引用计数加1,当一个对象...

43970
来自专栏数说工作室

统计师的Python日记【第八天:数据清洗(2)文本处理】

本文是【统计师的Python日记】第8天的日记 回顾一下: 第1天学习了Python的基本页面、操作,以及几种主要的容器类型。 第2天学习了python的函数、...

84860

扫码关注云+社区

领取腾讯云代金券

年度创作总结 领取年终奖励