YOLOX | MMDetection 复现保姆级解析

简介: 最近 YOLOX 火爆全网,速度和精度相比 YOLOv3、v4 都有了大幅提升,并且提出了很多通用性的 trick,同时提供了部署相关脚本,实用性极强。

640.png

首先感谢本次参与YOLOX算法复现工作的社区贡献者们 (Github 账号名):

HAOCHENYE、xiaohu2015、zhiqwang、HsLOL、shinya7y


最近YOLOX 火爆全网,速度和精度相比 YOLOv3、v4 都有了大幅提升,并且提出了很多通用性的 trick,同时提供了部署相关脚本,实用性极强。


640.png


近期,MMDetection 开源团队成员也组织进行了相关复现。通过与社区成员的协同开发,不仅让复现过程更加高效,而且社区成员在参与过程中可以不断熟悉算法,熟悉 MMDetection 开发模式。


后续我们也会再次组织相关复现活动,希望社区成员积极参与,共同成长,共同打造更加优异的目标检测框架。


本文内容

1. YOLOX 算法简介

2.YOLOX 复现流程全解析


1. YOLOX 算法简介



官方开源地址:

https://github.com/Megvii-BaseDetection/YOLOX


MMDetection 开源地址(欢迎  star):

GitHub - open-mmlab/mmdetection: OpenMMLab Detection Toolbox and Benchmark


复现相关 projects:

Support of YOLOX · open-mmlab/mmdetection


YOLOX 的主要特性可以归纳为:

 

· Anchor-free,无需设计 anchor,更少先验,减少复杂超参,推理较高效;


· 提出了 Decoupled Head,参考 FCOS 算法设计解耦了分类和回归分支,同时新增 objectness 回归分支;


· 为了加快收敛以及提高性能,引入了 SimOTA 标签分配策略,其包括两部分 Multi positives 和 SimOTA,Multi positives 可以简单的增加每个 gt 所需的正样本数,SimOTA 基于 CVPR2021 最新的 OTA 算法,采用最优传输理论全局分配每个 gt 的正样本,考虑到 OTA 带来的额外训练代价,作者提出了简化版本的 OTA ,在长 epoch 训练任务中 SimOTA 和 OTA 性能相当,且可以极大的缩小训练代价;


· 参考 YOLOV4 的数据增强策略,引入了 Mosaic 和 MixUp,并且在最后 15 个 epoch 时候关闭这两个数据增强操作,实验表明可以极大地提升性能;


· 基于上述实践,参考 YOLOV5 网络设计思路,提出了 YOLOX-Nano、YOLOX-Tiny、YOLOX-S、YOLOX-M、YOLOX-L 和 YOLOX-X 不同参数量的模型。


2. YOLOX 复现流程全解析



本节目录

   2.1 推理精度对齐

   2.2 训练精度对齐

         2.2.1 优化器和学习率调度器

         2.2.2  EMA策略

         2.2.3 Dataset

         2.2.4 Loss

         2.2.5 其他训练 trick



我们简单将 YOLOX 复现过程拆分为 3 个步骤,分别是:(1)推理精度对齐(2)训练精度对齐(3)重构。


#(偷偷注释掉)为了方便将官方开源权重迁移到 MMDetection 中,在推理精度对齐过程中,我们没有修改任何模型代码,而且简单的复制开源代码,分别插入 MMDetection 的 backbone 和 head 文件夹下,这样就只需要简单的替换模型 key 即可重复段落请忽略小编已哭晕。


2.1 推理精度对齐


为了方便将官方开源权重迁移到 MMDetection 中,在推理精度对齐过程中,我们没有修改任何模型代码,而且简单的复制开源代码,分别插入 MMDetection 的 backbone 和 head 文件夹下,这样就只需要简单的替换模型 key 即可。


一个特别需要注意的点:BN 层参数不是默认值 eps=1e-5, momentum=0.1,而是eps=1e-3, momentum=0.03,这个应该是直接参考 YOLOV5。


排除了模型方面的问题(后处理策略我们暂时也没有改),对齐推理精度核心就是分析图片前处理代码。其处理流程非常简单——


# 前处理核心操作
def preproc(image, input_size, mean, std, swap=(2, 0, 1)):
    # 预定义输出图片大小
    padded_img = np.ones((input_size[0], input_size[1], 3)) * 114.0
    # 保持宽高比的 resize
    img = np.array(image)
    r = min(input_size[0] / img.shape[0], input_size[1] / img.shape[1])
    resized_img = cv2.resize(
        img,
        (int(img.shape[1] * r), int(img.shape[0] * r)),
        interpolation=cv2.INTER_LINEAR,
    ).astype(np.float32)
    # 右下 padding
    padded_img[: int(img.shape[0] * r), : int(img.shape[1] * r)] = resized_img
    # bgr -> rgb
    padded_img = padded_img[:, :, ::-1]
    # 减均值,除方差
    padded_img /= 255.0
    if mean is not None:
        padded_img -= mean
    if std is not None:
        padded_img /= std
    padded_img = padded_img.transpose(swap)
    return padded_img, r

滑动可见完整代码


可以发现,其前处理流程比较简单:先采用保持宽高比的 resize,然后右下 padding 成指定大小输出,最后是归一化。


在 MMDetection 中可以直接通过修改配置文件来支持上述功能:

test_pipeline = [
    dict(type='LoadImageFromFile'),
    dict(
        type='MultiScaleFlipAug',
        img_scale=img_scale,
        flip=False,
        transforms=[
            dict(type='Resize', keep_ratio=True),
            dict(type='RandomFlip'),
            dict(type='Pad', size=(640, 640), pad_val=114.0),
            dict(type='Normalize', **img_norm_cfg),
            dict(type='DefaultFormatBundle'),
            dict(type='Collect', keys=['img'])
        ])
]



相关的后处理阈值为:

test_cfg=dict(  
    score_thr=0.001, 
    nms=dict(type='nms', iou_threshold=0.65)))


分别对 YOLOX-S 和 YOLOX-Tiny 模型权重在官方源码和 MMDetection 中进行评估,验证是否对齐,结果如下:


640.png

注意:由于官方开源代码一直处于更新中,现在下载的最新权重,可能 mAP 不是上表中的值。


文章来源:公众号【OpenMMLab】

2021年8月11日

目录
相关文章
|
JSON JavaScript 前端开发
Gson与Fastjson两种Json解析神器保姆级使用攻略
Gson与Fastjson两种Json解析神器保姆级使用攻略
400 0
Gson与Fastjson两种Json解析神器保姆级使用攻略
|
JSON JavaScript 前端开发
JavaScript入门保姆级教程 ——— 重难点详细解析(万字长文,建议收藏)
基本语法、事件 🍅 Java学习路线:搬砖工的Java学习路线 🍅 作者:程序员小王 🍅 程序员小王的博客:https://www.wolai.com/wnaghengjie/ahNwvAUPG2Hb1Sy7Z8waaF 🍅 扫描主页左侧二维码,加我微信 一起学习、一起进步 🍅 欢迎点赞 👍 收藏 ⭐留言 📝
102 0
JavaScript入门保姆级教程 ——— 重难点详细解析(万字长文,建议收藏)
|
XML Java 应用服务中间件
监听器与过滤器保姆级解析
Filter 过滤器它是 JavaWeb 的三大组件之一。三大组件分别是:Servlet 程序、Listener 监听器、Filter 过滤器。 Filter 过滤器它是 JavaEE 的规范。也就是接口,它的作用是:拦截请求,过滤响应。
监听器与过滤器保姆级解析
|
JSON 前端开发 JavaScript
Gson与Fastjson两种Json解析神器保姆级使用攻略
Gson与Fastjson两种Json解析神器保姆级使用攻略
Gson与Fastjson两种Json解析神器保姆级使用攻略
|
6天前
yolo-world 源码解析(六)(2)
yolo-world 源码解析(六)
16 0
|
6天前
yolo-world 源码解析(六)(1)
yolo-world 源码解析(六)
8 0
|
7天前
yolo-world 源码解析(五)(4)
yolo-world 源码解析(五)
16 0
|
7天前
yolo-world 源码解析(五)(1)
yolo-world 源码解析(五)
30 0

推荐镜像

更多