文章目录
【YOLO系列】YOLO v3(网络结构图+代码)
【YOLO 系列】YOLO v4-v5先验知识
【YOLO系列】YOLO v4(网络结构图+代码)
我是在自己笔记本上配置的YOLO v5环境。首先,conda创建YOLO v5虚拟环境,克隆
ultralytics/yolov5项目,pip install -r requirements.txt安装所需库文件。
YOLO v5提供了五个不同大小的预训练模型,分别是YOLOv5n、YOLOv5s、YOLOv5m、YOLOv5l和YOLOv5x。这五个模型的参数量、mAP和推理速度如下所示:
这五个模型的网络结构是一样的,不一样的就是通道数和宽度不一样,受depth_multiple和width_multiple两个因子影响。
模型depth multiplewidth multipleYOLOv5n0.330.25YOLOv5s0.330.50YOLOv5m0.670.75YOLOv5l1.01.0YOLOv5x1.331.25
推理
我笔记本的CPU为Inter i7-7700HQ,使用detect.py进行推理。预训练权重选择yolov5x.pt,推理图像默认来自于"\data\images"文件夹下。推理命令行如下所示:
python detect.py --weights models/yolov5x.pt --device cpu --view-img
推理时,会输出每张图片前处理后的图片大小,检测结果和推理时间。官方给出的YOLOv5x在CPU上的推理时间为766ms,可能笔记本的CPU太弱了吧,这两张图片的推理时间在1.5s~2.0s之内。
image 1/2 F:\yolov5\data\images\bus.jpg: 640x480 4 persons, 1 bus, 1973.8ms
image 2/2 F:\yolov5\data\images\zidane.jpg: 384x640 3 persons, 2 ties, 1565.6ms
Speed: 0.5ms pre-process, 1769.7ms inference, 7.8ms NMS per image at shape (1, 3, 640, 640)
bus图片推理结果展示zidane图片推理结果展示
转换onnx
YOLO v5的模型配置是yaml文件,为了能直观地查看YOLO v5的网络结构,需要将预训练pt模型转换成onnx的格式。onnx的算子版本默认为17,这里设置算子版本为11。
python export.py --weights models/yolov5x.pt --device cpu --opset=11 --include onnx
然后使用生成的onnx文件进行推理,测试一下生成的onnx文件是否正确。
F:\yolov5>python detect.py --weights models/yolov5x.onnx --device cpu --view-img
网络架构
YOLO v5的网络结构也清晰地分为backbone、Neck和Head三部分。YOLO v5第一版于2020年6月发布,距今已有三年,这三年YOLO v5也从第一版已更新到第七版。在前四版时,对PAN和CSP都进行了更新。在第四版时,使用SiLU激活函数代替LeakyReLU和Hardswish激活函数。在第六版时,使用一个
Conv(k=6, s=2, p=2)
卷积层替代Focus结构;使用SPPF替代SPP结构。还有一些其他更改,目的都是为了使得YOLO v5模型更轻量、更快和更准确。
自YOLO v5模型第六版之后,backbone、neck和Head的结构就如下所示了。
- Backbone: New CSP-Darknet 53
- Neck: SPPF, New CSP-PAN
- Head: YoLo v3 Head
下图是YOLOv5l的网络架构,YOLO v5在Head时,使用C3结构替代YOLOv3和YOLOv4 head和neck的五层卷积。
SPP VS SPPF
SPPSPPF
SPPF比SPP的运行时间快2倍。SPP的三个最大池化层的size是不一样的,但是输入是一样的;SPPF的三个最大池化层的size是一样的,后续两个最大池化的输入是前一个最大池化层的输出。
AutoAnchor
在YOLO v5中,默认使用autoAnchor,不用手工选择anchor boxes,使用k-means聚类算法在训练集上自动寻找anchor boxes。训练时设置noautoanchor,才能使用自定义的anchor boxes。
parser.add_argument(‘–noautoanchor’, action=‘store_true’, help=‘disable AutoAnchor’)
autoAnchor在yaml配置文件中设置如下所示。其中3表示每个输出层分配3个anchor大小。
anchors: 3 # AutoAnchor evolves 3 anchors per P output layer
k-means是非常经典的聚类方法,通过计算样本之间的距离将相近的样本聚到同一类别。auto anchor的计算函数为utils/autoanchors.py文件的kmean_anchors。源代码有些长,我只截取了k-means计算auto anchor的核心部分和进化算法中的适应度计算。
defmetric(k, wh):# compute metrics"""
k: anchor框
wh: 整个数据集的 wh [N, 2]
x: [N, 9] N个 gt boxes 与所有 anchor boxes的宽比或高比(两者之中较小者)
x.max(1)[0]: [N] N个 gt boxes 与所有 anchor boxes中的最大宽比或高比(两者之中较小者)
"""
r = wh[:,None]/ k[None]# 两者的重合程度越高,越趋近1
x = torch.min(r,1/ r).min(2)[0]# ratio metricreturn x, x.max(1)[0]# x, best_xdefanchor_fitness(k):# mutation fitness#适应度计算 用于遗传算法中衡量突变是否有效的标注 优胜劣汰
_, best = metric(torch.tensor(k, dtype=torch.float32), wh)return(best *(best > thr).float()).mean()# fitness# 得到数据集中所有图像的wh
shapes = img_size * dataset.shapes / dataset.shapes.max(1, keepdims=True)# 将图片的长边缩放到img_size,相应地缩放短边
wh0 = np.concatenate([l[:,3:5]* s for s, l inzip(shapes, dataset.labels)])# 将图片中gt boxes的wh缩放到shapes尺度。 dataset.labels其中格式为[类别,x, y , w, h],xywh均已经归一化了# Filter
i =(wh0 <3.0).any(1).sum()# 统计gt boxes中w和h小于3像素的个数if i:
LOGGER.info(f'{PREFIX}WARNING ⚠️ Extremely small objects found: {i} of {len(wh0)} labels are <3 pixels in size')# 筛选大于2像素的gt boxes用作聚类
wh = wh0[(wh0 >=2.0).any(1)].astype(np.float32)# filter > 2 pixels# Kmeans inittry:
LOGGER.info(f'{PREFIX}Running kmeans for {n} anchors on {len(wh)} points...')assert n <=len(wh)# apply overdetermined constraint# 计算wh的标准差
s = wh.std(0)# sigmas for whitening# 聚类
k = kmeans(wh / s, n,iter=30)[0]* s # pointsassert n ==len(k)# kmeans may return fewer points than requested if wh is insufficient or too similarexcept Exception:
LOGGER.warning(f'{PREFIX}WARNING ⚠️ switching strategies from kmeans to random init')
k = np.sort(npr.rand(n *2)).reshape(n,2)* img_size # random init
wh, wh0 =(torch.tensor(x, dtype=torch.float32)for x in(wh, wh0))
k = print_results(k, verbose=False)
Loss
YOLO v5的loss也由三部分组成,Classes loss和Objectness loss都使用的是BCE loss,Location loss为CIoU loss。三个预测层的Objectness loss是有不同权重的,小中大分别是[4.0, 1.0, 0.4]。
YOLO v5更新了YOLO v3中已知偏移量
c
x
,
c
y
,
t
w
,
t
h
c_{x},c_{y},t_{w},t_{h}
cx,cy,tw,th计算预测bbox的公式,公式对比如下所示:
YOLO v3YOLO v5
更新公式之后,中心点偏移量的取值范围由
(
0
,
1
)
\left( 0, 1\right)
(0,1)调整到
(
−
0.5
,
1.5
)
\left( -0.5, 1.5\right)
(−0.5,1.5),因此,偏移量更容易得到0或者1。在YOLO v3的box方程中,宽度和高度无上限,这是一个严重的缺陷,它可能会导致梯度失控、不稳定性、NaN loss等问题,并最终导致无效训练。
中心点对比宽度和高度对比
参考
- ultralytics/yolov5
- Architecture Summary
版权归原作者 马鹤宁 所有, 如有侵权,请联系我们删除。