使用Matplotlib库可视化COCO数据集格式常用函数 (一)

前言

经常使用COCO格式数据集的同学们肯定会经常对模型的输出结果进行可视化,可视化最常用的包是matplotlib.pyplot,下面就让我们看一下如何使用plt包对COCO格式的数据进行可视化。

这是第一部分,主要讲解用plt的原理和基本使用方法,对于COCO数据集的可视化可以直接看第二部分。

理论知识

matplotlib.pyplot是python中画图常用的包,在使用前通常用import matplotlib.pyplot as plt引入,以下都用plt代替这个包。

plt包中有l两个重要的对象:Figure(画布对象)aiex(子图对象)
figure对象就是一个空白的画布子图对象就是画布上一块内容(这块内容可以显示图表,也可以显示图像),一个画布上可以有多个子图,所以也就有下文将要讲的多子图显示技术。

举个例子,figure对象可以使用plt.figure()创建,然后使用plt.show()进行显示,此时结果如下图,可以看到因为画布上没有任何子图对象,所以是空白的。

在这里插入图片描述
有了上面的理论,我们就有了一个直观的认识:当我们使用plt进行可视化时,无论是显示单个子图还是多个子图,首先要做的就是创建一个空白的画布对象,然后创建一个个子图对象,在对应的子图上进行相应的操作。

有些同学可能会问,显示图片的时候直接用plt.imshow(image)就可以了啊,也没有手动创建一个Figure对象,这是因为这个函数内部自己新建了一个画布对象~

好了,有了前面知识的铺垫,就让我们从最简单的显示单张图片开始看一下到底如何使用plt包进行绘图吧!

在单个子图上显示、保存图片

如果显示图片,可以使用plt.imshow(image,cmap=''),其中image_path代表图片,可以是io.imread()读取的Image对象,cmap代表图片的色彩空间,默认是RGB。如果显示灰度图片,需要让cmap='gray'才能正确显示。

为了使图片显示在屏幕上,调用上面的函数后还需要调用plt.show()使画布绘制在桌面上。

如果保存图片,可以使用plt.savefig(image_name)保存当前画布中的内容,其中,image_name代表所要保存的路径和文件名。

在多个子图上显示图片

上面的例子我们在一个子图上显示了图片,但是如果我们想要用多个子图显示不同的图片应该怎么做呢?

首先应该在建好的空白画布上创建子图对象,然后使用plt.subplot(row, col, idx)在子图上绘制图片,其中row代表画布的行数,col代表画布的列数,idx表示当前激活的子图下标,下标从1开始,按从左往右的顺序依次递增。

为什么还需要传入子图的坐标呢?这是因为这样做即使我们不用变量接收子图对象,plt包也可以正确地知道接下来的操作应该在哪个子图上执行。具体代码如下:

I = io.imread('C:/Users/hejianfei/Desktop/ski10病理切片/001-houqi-077.jpg')
plt.subplot(1, 2, 1)  # 子图分为一行两列,当前选择第一个
plt.imshow(I)  # 显示图片
plt.subplot(1, 2, 2)  # 子图分为一行两列,当前选择第二个
plt.imshow(I)   
plt.show()

或者也可以手动得到每个子图对象,然后在子图对象上显示图片

I = io.imread('C:/Users/hejianfei/Desktop/ski10病理切片/001-houqi-077.jpg')
ax = plt.subplot(1, 2, 1)  # 用ax接收当前子图对象
ax.imshow(I)  # 显示图片
ax = plt.subplot(1, 2, 2)
ax.imshow(I)
plt.show()

最终的结果是一样的,如下:
在这里插入图片描述

在图片上绘制检测框

上面我们知道了如何在多个子图上显示图片,现在来考虑如何在图片上绘制检测框。

先来考虑如何实现这个功能,为了实现效果,我们肯定需要先显示出图片,然后再在原图上叠加上检测框,那么如何实现叠加的效果呢?

plt包中有一个ax.add_patch(obj)函数可以实现这个功能,其中ax代表当前的子图实例,obj是plt包内置的形状类,可以是矩形,椭圆,多边形等等,这里我们主要用矩形类(绘制检测框)和多边形类(绘制掩码)。

检测框就是一个矩形框,可以用左上角坐标和右下角坐标来表示这个矩形。plt包中有专门的Rectangle类来表示一个矩形,关于此类详细的用法可以百度。

具体代码如下:

I = io.imread('C:/Users/hejianfei/Desktop/ski10病理切片/001-houqi-077.jpg')
# 实例化矩形对象:设置边框的宽度,边框的颜色,填充颜色
rect = plt.Rectangle((0.0, 0.0), 100, 100, alpha=0.8, linewidth=1, edgecolor='r', facecolor='none')
ax = plt.subplot(1, 2, 1)  # 用ax接收当前子图对象
ax.imshow(I)  # 显示图片
ax.add_patch(rect)  # 在已有的图片上添加其他对象
ax = plt.subplot(1, 2, 2)
ax.imshow(I)
plt.show()

我们在第一个子图上显示了一个矩形框,结果如下:

在这里插入图片描述
如果要绘制mask,可以借助plt包中的多边形类(Poly)来实现,下面介绍COCO时会讲到。

多子图显示图片,设置窗口的属性(名称,坐标范围)

上面创建多个子图时,使用的函数为plt.subplot()函数。实际上,还有一个常用的函数plt.add_subplot()函数也可以用来创建子图。

二者的不同在于,在使用plt.subplot()函数前,不需要手动调用plt.figure()函数创建一个画布对象,而在使用plt.add_subplot函数前需要手动调用plt.figure()函数创建一个画布对象,具体代码如下:

I = io.imread('C:/Users/hejianfei/Desktop/ski10病理切片/001-houqi-077.jpg')
# ax = plt.subplot(1, 2, 1)  # 用ax接收当前子图对象
# ax.imshow(I)  # 显示图片
# ax = plt.subplot(1, 2, 2)
# ax.imshow(I)
# plt.show()

fig = plt.figure()  # 创建figure对象
ax = fig.add_subplot(1, 2, 1)  # 添加子图
ax.imshow(I)
ax = fig.add_subplot(1, 2, 2)
ax.imshow(I)
plt.show()

多子图显示时可以通过ax.set_title()函数设置子图名称,ax.set_xlim(-10, 20) ax.set_ylim(-10, 20)设置子图显示的坐标范围,具体代码如下:

fig = plt.figure()
titles = ['iou', 'giou', 'diou', 'ciou']
for i in range(4):
   ax = fig.add_subplot(2, 2, i + 1)
   ax.set_title(titles[i])
   rect1 = plt.Rectangle(
       (recs[i*2][0][0], recs[i*2][0][1]),  # (x,y)矩形左下角
       recs[i*2][0][3] - recs[i*2][0][1],  # width长
       recs[i*2][0][2] - recs[i*2][0][0],  # height宽
       color='maroon',
       alpha=0.5)
   ax.add_patch(rect1)
   rect2 = plt.Rectangle(
       (recs[i * 2 + 1][0][0], recs[i * 2 + 1][0][1]),  # (x,y)矩形左下角
       recs[i * 2 + 1][0][3] - recs[i * 2 + 1][0][1],  # width长
       recs[i * 2 + 1][0][2] - recs[i * 2 + 1][0][0],  # height宽
       color='green',
       alpha=0.5)
   ax.add_patch(rect2)
   ax.set_xlim(-10, 20)
   ax.set_ylim(-10, 20)
plt.show()
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值