安装错误
no such file or directory: 'pycocotools/_mask.c'
解决办法: pip install cython
评价标准
COCO数据集介绍
COCO数据集具有5种标签类型, 分别为: 目标检测, 关键点检测, 物体分割, 多边形分割 以及 图像描述. 这些标注数据使用JSON
格式存储. 所有文件除了标签项以外都共享同样的数据结构, 如下所示:
标签结构各有不同, 如下所示:
Object Detection
每一个目标实例的标签都具有一系列条目, 包括该目标的类别id以及分割掩膜(segmentation mask). 分割掩膜的格式取决于实例表示的是一个单一的目标(iscrowd=0, 使用polygons标注)还是一群目标(iscrowd=1, 使用RLE标注). 注意, 一个单一的物体(iscrowd=0)在被遮挡的情况下, 可能会需要多个多边形来表示. Crowd标签用来标注一大群目标(如一群人). 另外, 每一个物体都会提供一个闭合的bounding box( box的坐标系从图左上角开始,0-indexed). 最后, 标注结构的类别条目存储着从cat id 到类别的映射以及超类别的名字.
关键点检测
Stuff Segmentation
Stuff Segmentation的格式和object detection的格式几乎一模一样, 但是stuff segmentation无需iscrowd
条目, 因为该条默认置为0. 为了方便访问, coco提供了json和png两种标注格式. 在 json 格式中, 每一个出现在图片中的类别都会单独用一个RLE标签条目编码(也就是说同类的会被放到同一个RLE编码里面). category_id 则代表当前的物体类别的id.
Panoptic Segmentation
数据集信息
标注格式
COCO-API 使用方法及源码解析
利用 json 文件实例化 COCO API 对象
- 参数
-annotation_file=None
(str): location of annotation file
1 | from pycocotools.coco import COCO |
coco.createIndex()
COCO 的构造函数会调用该函数来建立数据索引, 用户通常不会直接调用该函数
参数: 无
返回: 无
调用后会输出:1
2
3
4loading annotations into memory...
Done (t=0.74s)
creating index...
index created!
coco.info()
参数: 无
返回: 无
调用后会打印数据集标签的相关信息1
2
3
4
5
6description: COCO 2017 Dataset
url: http://cocodataset.org
version: 1.0
year: 2017
contributor: COCO Consortium
date_created: 2017/09/01
coco.getAnnIds()
- 参数:
imgIds=[]
(int array) : 返回指定 imgs id 的 annotations id 列表catIds=[]
(int array) : 返回指定类别 id 的所有 annotations id 列表areaRng=[]
(float array, 二元组, 指定面积区间大小) : 返回area
项标签处于指定区间的 annotations id 列表iscrowd=None
(boolean):
- 返回: 返回满足条件的 annotations 的 id, 如果三个列表参数均为空, 则直接返回所有的 id. 注意上面三个参数的筛选过程是逐步进行的, 前者筛选后的结果会作为后者筛选的输入, 若三项同时为空, 则会返回所有的类别编号
coco.getCatIds()
- 参数(当传入单个字符串时, 会自动转换成只包含一个字符串元素的列表):
catNms=[]
(str array) : 返回列表中指定的类别名称的类别编号supNms=[]
(str array) : 返回列表中指定的子类别名称的类别编号catIds=[]
(int array) : 返回指定类别编号对应的类别编号
- 返回
ids
(int array) : 类别编号, 注意上面三个参数的筛选过程是逐步进行的, 前者筛选后的结果会作为后者筛选的输入, 若三项同时为空, 则会返回所有的类别编号
coco.getImgIds()
- 参数:
imgIds=[]
(int array) : 返回指定 img ids 的 img idscatIds=[]
(int array) : 返回具有指定类别 ids 的 img ids
- 返回: 符合条件的图片的 id, 若参数均为空, 则返回所有的图片 id
coco.loadAnns()
- 参数:
ids=[]
(int array) : 加载指定 ann ids 的 ann
- 返回: 一个元素均为字典类型的列表, 其中字典的键根据任务的不同可能包含:
- segmentation:
- area:
- iscrowd: 布尔值, 表示是否是群体目标(不好检测及分割)
- image_id: 代表当前框属于哪一张图片
- bbox: 代表 bbox 的坐标, 分别为 [x,y,width,height]
- category_id: 代表当前的类别编号
- id: 当前框的 id, 也就是输入参数 ann ids 的值
注意, 参数为空时会返回一个空列表
coco.loadCats()
加载类别信息
- 参数:
ids=[]
(int array): 类别编号 cat ids - 返回: 一个元素均为字典类型的列表, 字典的键包含:
- supercategory: 分别代表大类别(如交通工具)
- id: 类别编号 cat ids
- name: 以及类别的名称(如飞机). 注意, 参数为空时会返回一个空列表
coco.loadImgs()
加载图片信息
- 参数:
ids=[]
(int array): 图片编号 img ids - 返回: 一个元素均为字典类型的列表, 字典的键包含:
- license
- file_name: 图片的本地文件名
- coco_url: 可以在线访问的图片地址
- height: 图片的高
- width: 图片的宽
- data_captured
- flickr_url, id
coco.showAnns()
先标签的信息显示出来(前面的 load 函数只是加载)
参数没有默认值, 调用函数时必须指定
- 参数:
anns
(array of object), 传入的需要是 loadAnns() 函数返回的 anns 对象列表 - 返回: 无
该函数需要先用import matplotlib.pyplot as plt
创建相应的画布并加载图片才能看到最终的可视化效果, 具体见如下代码所示
1 | import matplotlib.pyplot as plt |
coco.loadRes()(待尝试)
加载算法结果, 同时创建API以便访问它们, Load algorithm results and create API for accessing them.
- 参数:
resFile
(sre): 文件名称或者 result file, 无默认值, 必须指定 - 返回: result pai object
coco.download()
从Mscoco.org.server上下载COCO数据集
coco.loadNumpyAnnotations()
从 numpy 数组中转换算法的结果, 其结果是一个 Nx7 大小的数组
- 参数:
data
(numpy.ndarray), Nx7, {imageId, x1, y1, w, h, score, class} - 返回: annotations(python nested list)
coco.annToRLE
只能接受一个 ann 对象, 不能是多个 ann 组成的列表
- 参数:
ann
, 将 polygons 或者 uncompressed RLE 类型的数据转换成 RLE - 返回: rle 类型的数据
coco.annToMask
只能接受一个 ann 对象, 不能是多个 ann 组成的列表
- 参数:
ann
, 将 polygons, uncompressed RLE 或者 RLE 类型的数据转换成二值掩膜 - 返回: 二值掩膜
encode()
将 binary masks 编码成 RLE 形式
- 参数:
bimask
- 返回: RLE 类型的数据
decode()
将 RLE 形式解码成 binary masks
- 参数:
rleObjs
, rle 类型的输入 - 返回: 解码后的二值掩膜
area()
- 参数:
rleObjs
, rle 类型的输入 - 返回: 分割区域的面积
toBbox()
源码解析
最常用的是 pycocotools/coco.py
文件中的COCO
类, 其内部实现如下:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55# pycocotools/coco.py
# 首先, 是一大串的注释
# COCO API提供了一系列的辅助函数来帮助载入,解析以及可视化COCO数据集的annotations
# 该文件定义了如下API 函数:
# COCO - COCO api 类, 用于载入coco的annotation 文件, 同时负责准备对应数据结构来存储
# decodeMask - 通过rle编码规范, 来对二值mask M进行解码
# encodeMask - 使用rle编码规范来对二值mak M进行编码
# getAnnIds - 获得满足给定过滤条件的ann ids(标注)
# getCatIds - 获得满足给定过滤条件的cat ids(类别)
# getImgIds - 获得满足给定过滤条件的img ids(图片)
# loadAnns - 根据指定的ids加载anns
# loadCats - 根据指定的ids加载cats
# loadImgs - 根据指定的ids加载imgs
# annToMask - 将annotation里面的segmentation信息转换成二值mask
# showAnns - 可视化指定的annotations
# loadRes - 加载算法结果同时创建API以便访问它们
# download - 从Mscoco.org.server上下载COCO数据集
# 接下来, 具体看一下COCO类的实现
class COCO:
def __init__(self, annotation_file=None):
# 构造函数
# 参数annotation_file: 指定了annotation文件的位置
# dataset, anns, cats, imgs均为字典类型数据
self.dataset, self.anns, self.cats, self.imgs = dict(), dict(), dict(), dict()
# imgToAnns, catToImgs均为defaultdict数据类型(带有默认值的字典)
self.imgToAnns, self.catToImgs = defaultdict(list), defaultdict(list)
if not annotation_file == None:
#...
# 以只读方式加载json标注文件
dataset = json.load(open(annotation_file, 'r'))
assert type(dataset)==dict # 确保读出来的是字典类型
#...
# 正式将读取的字典数据赋给该类的成员变量
self.dataset = dataset
# 创建索引
self.createIndex()
def createIndex(self):
# 创建索引
# 三个都是字典数据类型
anns,cats,imgs={},{},{}
# 两个defaultdict数据类型
imgToAnns, catToImgs = defaultdict(list), defaultdict(list)
if 'annotations' in self.dataset:
for ann in self.dataset['annotations']:
xml 数据转成 COCO 数据
对于 COCO 数据格式, 我们需要利用 json 模块来构建, 不同的任务需要的标签各不相同, 对于目标检测任务来说, 我们需要如下标签信息:
- info: 数据集相关信息, 主要是数据集的相关信息, 训练时不会用到
- images: 图片相关信息, id, 宽, 高, 文件名(最重要的四个)等
- annotations: 标签相关信息, 目标检测任务需要 bbox, 对应的类别编号, 以及所属图片编号
- license: 训练时不会用到, 随便填
通用模板如下:
1 | import sys |