博客:
深度学习中的目标检测网络中的one stage和two stage?
目标检测——One-stage和Two-stage的详解
深度学习: one-stage/two-stage/multi-stage 目标检测算法
基于的现在目标检测算法中有三个组件:Backbone
、Neck
和Head
:
(1)Backbone,译作骨干网络,主要指用于特征提取的,已在大型数据集(例如ImageNet|COCO等)上完成预训练,拥有预训练参数的卷积神经网络,例如:ResNet-50、Darknet53等;
(2)Head,译作检测头,主要用于预测目标的种类和位置(bounding boxes);
(3)Neck,在Backone和Head之间,会添加一些用于收集不同阶段中特征图的网络层;
简而言之,基于深度学习的目标检测模型的结构是这样的:input->backbone->neck->head->output
。
主干网络提取特征,脖子提取一些更复杂的特征,然后头部计算预测输出。
(1)input: Image, patches, image pyramid,… …
(2)Backbone: VGG-16, ResNet-50, ResNeXt-101, Darknet53, 轻量级backbone(MobileNet, ShuffleNet, EfficientNet, … …)
(3)Neck:
(4)Head:
简单来说下游任务是具体部署,上游任务是训练模型。
(1)上游任务:
预训练模型。一般就是利用上游数据上进行预训练,以生成一个包含视觉表征的模型。
(2)下游任务:
下游任务是计算机视觉应用程序,用于评估通过自监督学习学习到的特征的质量。当训练数据稀缺时,这些应用程序可以极大地受益于预训练模型。
下游任务更多的是评估任务,相当于项目落地,需要去做具体任务来评价模型好坏。如目标检测、语义分割等。
Object Detection
主要分为以下2个支系:
指标 | one-stage | two-stage |
---|---|---|
主要算法 | YOLOv1、SSD、YOLOv2、RetinaNet、YOLOv3 | Fast R-CNN、Faster R-CNN |
检测精度 | 较低 | 较高 |
检测速度 | 较快 | 较慢 |
典型代表 | YOLOv1 | Fast R-CNN |
状态 | 存在 | 存在 |
Object Detection
的主要任务:
1.对于不需要预生成RP的Detection算法而言,算法只需要完成三个任务:
2.对于有预生成RP的Detection算法而言,算法要完成的主要有四个任务:
【Multi-Stage】:
最早期的检测算法 (主要为R-CNN、SPPNet) 都属于multi-stage系。这个时候的Selective Search、Feature extraction、location regressor、cls SVM是分成多个stage来各自单独train的。
【Two-Stage】:
到了Fast R-CNN的时候,Feature extraction、location regressor、cls SVM都被整合到了一个network里面,可以实现这三个task一起train了。由于生成RP的task还需要另外train。
【One-Stage】:
在YOLOv1中,“生成RP”这一任务被直接丢弃了。因此,整个算法只剩下了一个stage。
One-Stage
:直接回归物体的类别概率和位置坐标值(无region proposal),但准确度低,速度快。
输入一个Tensor(原图像),输出一个代表结果的Tensor,其中编码了目标的位置信息和类别概率;
在通用目标检测任务,最早的one-stage工作大概可以追溯到YOLOv1,它最大的亮点就是它只需要一个单一的网络就能够同时完成定位和分类两件事。因此,这样的网络训练起来必然能够真正地端到端、推理的时候速度也必然会更快。
事实上,YOLO的这种做法其实就是对two stage中的RPN的合理扩展。前面已经说过,RPN网络就干一件事,处理输入图像,最后输出包含前景信息的RoI,这里,我们稍微想得细一些,RPN其实它同时完成了定位和分类两件事,定位就是输出RoI的边界框坐标,分类就是判别是前景还是背景。
就结果来看,我们说RPN是得到了RoI,完成了定位,但就过程而言,它还做了分类,只不过分类的分类是前背景,而不是我们感兴趣的阿猫阿狗之类的。
如图所示,YOLO仅靠一个网络输出同时包含了坐标和类别置信度的tensor,实际上,不难看出来,YOLO这是将Faster R-CNN的两部分的任务都捏合进了RPN一个网络里。
它的主要学习任务一共包括三个:
(1)前景背景的分类学习(objectness)
(2)类别的分类学习(classification)
(3)边界框坐标的学习(regression)
其中,objectness的学习是全局的,即feature map上的所有grid cell都要去参与学习,这是理所当然的,毕竟要区分前景和背景,这理应是个全局任务;
classification和regression则不然,只有包含了前景信息的grid cell会去学习,背景是不学习的,这同样也是理所当然的,背景不需要分类和定位。
后来,其他的one-stage检测器如SSD和RetinaNet则又将YOLO的学习方式简化一下,上面说到,YOLO一个包含三个,这还是不够干脆,那么SSD和RetinaNet就干脆把前景背景的学习和类别的学习捏合到一块去。
假设一个有10个类别,那么,现在要学习11个类别,这多出来的一个类别就是背景,现在的feature map上的每一个位置,要么就是背景,要么就是前景中的某一个类别(单标签任务)或多个类别(多标签任务)。
于是,我们可以看到,除了YOLO检测器外,现在大多数的one stage检测器最终就只有分类和回归两个分支。当然,这只是细节上的变化,不涉及本质。
Two-Stage
:先由算法生成一系列作为样本的候选框,再通过CNN进行样本分类。
即整个目标检测工作需要两阶段完成。第一阶段先要生成候选包围框,即传说中的proposals,该阶段为后续的第二阶段提供可能出现目标的位置,然后再在第二阶段从这些候选框中辨别真正的目标物(当然还包括位置的微调)。
在通用目标检测技术领域中,最早的two stage检测器可以追溯到R-CNN,如图所示,其技术框架总共分为三步:
第一步是从输入图像中抽取感兴趣区域(Region of Interest),简称RoI,RoI中可以包含我们想要检测的目标,这一步其实相当于是对目标先定位;
第二步是抽取每一个RoI的特征,不少CV任务都是在high-level特征上去做的,那时候CNN技术也兴起来了,所以,第二步就正好由一个CNN网络去抽取特征;
第三步就是使用一个多分类SVM来识别每个RoI的类别,其实,第二步和第三步可以统一化到一个子框架里,即“分类”。
RCNN看似走了三步,实际上是先后做了两件事,先定位,后识别。
随后,在R-CNN的基础上,又诞生了Fast R-CNN和Faster R-CNN,先后优化了R-CNN的速度和精度上的一些缺陷。Faster R-CNN彻底将two stage工作的范式定了下来:
1.使用Region Proposal Network(RPN)处理输入图像,最终输出若干个RoI(这当中利用了anchor box,但这不是核心,即便anchor free也可以做RPN网络,如FCOS)并。这一步主要是完成了定位。
2.使用RoI pooling和若干fully connected layers完成对每一个RoI的类别识别。这一步主要是完成分类。
由此可见,two stage工作就是将detection任务拆成先定位、后识别的任务。
先定位主要就是为了将有用的前景信息尽可能多地保留下来,滤除掉对后续任务无用的背景信息,随后,再去分别那些前景信息,当然,这当中必然还会有一些背景信息要被识别出来,但相较于直接输入一张图像或者是被CNN处理的feature map,two stage的这种分类做法还是要精细得多,需要处理的目标几乎都是前景,只需要关心能不你识别对就行。即便需要识别的类别再多,可对RPN可言,它需要判别的目标就是前景和背景,它需要做好的事就是尽可能把前景都抠出来,丢掉背景。
但在训练的时候,会有一些棘手的问题要处理一下,具体来说,我们通常会限制RPN给出的RoI个数,且给出的RoI质量也要高一些,诸如NMS等后处理操作是不可少的,这当中存在的一些剪切操作就会导致梯度无法回传的问题,即从后续的RoI pooling回传的梯度因为这些“切片”操作而无法将梯度有效地回传给RPN。
因此,two stage检测器往往是交替训练两部分。不过,后来经过一些学者的精心设计,two stage也能够以端到端的训练,简单来说就是将两部分的loss加一块,一起回传,从整体来看,确实也是端到端。不过,这种端到端和我们训练一个CNN分类器的端到端还是不太一样。