AnchorBoxes

使用锚点框(AnchorBoxes)可以帮助目标检测网络更快速的收敛到真值框(GroundTruth)。关于锚点框的实现也经历了多次迭代变化:YOLOv2/YOLOv3/YOLOv4/YOLOv5

YOLOv2

YOLOv2首次使用锚点框来提高目标检测网络的性能。YOLOv2使用kmeans聚类算法来计算锚点,其中距离函数是质心和标注框之间的IoU。

目前在网络上找到3个相关的实现:

  1. 官方实现:darknet/scripts/gen_anchors.py
    1. 代码中采用了voc的训练集标注框数据进行计算,参考darknet/scripts/voc_label.py,可以发现采用了VOC2007 + VOC2012 train/val数据集
  2. 其他实现:
    1. jinyu121/get_anchor.py
    2. 部分参考了官方实现,增加了sklean的kmeans实现
    3. lars76/kmeans-anchor-boxes
    4. 几年前调研过:[YOLO][k-means聚类]寻找锚点

在Darknet官网上找到几个YOLOv3配置文件:

从配置文件来看,针对VOC数据集,作者生成了5个锚点框

YOLOv3

YOLOv3优化了锚点框的计算,它使用kmeans++算法来加速锚点框的生成。没有在网上找到相关源码实现,不过从官网的issues可以发现作者采用了kmeans++进行锚点框的生成

官网也提供了配置文件:

YOLOv4

类似于YOLOv3实现,不过具体的锚点框数值也发生了变化

YOLOv3和YOLOv4的测试环境设置也发生了变化,比如测试图像大小发生了变化,估计和这个会有关系。

YOLOv5

ultralytics/yolov5自定义了锚点框的生成,关键代码位于文件:yolov5/utils/autoanchor.py,其包含了3个函数:

  1. check_anchor_order(m):锚点框列表的大小顺序和Detect模块的步长列表(stride)保持一致。针对浅层特征层,采用更小的锚点框坐标,用于小目标的预测;针对深层特征层,采用更大的锚点框坐标,用于大目标的预测;
  2. check_anchors(dataset, model, thr=4.0, imgsz=640):检查配置文件中的锚点框是否和数据集匹配,衡量标准是BPR (Best Possible Recall,最佳召回率)
  3. kmean_anchors(dataset="./data/coco128.yaml", n=9, img_size=640, thr=4.0, gen=1000, verbose=True):锚点计算函数。yolov5使用scipy的kmeans算法实现,同时增加了以下优化:
    1. 过滤宽或者高==1.0的极小目标;
    2. 进行聚类计算前,白化宽高列表;
    3. 通过kmeans得到锚点框后,使用遗传算法来进化锚点以获得更好的匹配度。

相关阅读