在上一篇教程中,我向您介绍了Yolo v3算法的背景、网络结构、特征提取,最后,我们使用原始权重进行了简单的检测。在这一部分中,我将介绍YOLO v3损失函数和模型培训。I?uro™将介绍YOLO v3损失函数和模型培训。我们将在™数据集上培训一个自定义对象检测器。previous tutorial
损失函数
在YOLO v3中,作者将目标检测任务看作是目标区域预测和类别预测的回归问题,因此其损失函数有所不同。对于损失函数,Redmon J没有在Yolo v3论文中详细解释。但我在这个链接中找到了Yolo损失解释;损失函数如下所示:Yolo v3 paper this link
不过,通过对暗网源代码的解读,YOLO v3的损耗函数可以总结如下:
- 置信度损失,判断预测帧中是否有对象;
- 框回归损失,仅当预测框包含对象时计算;
- 分类损失,决定预测框架中的事物属于哪个类别。
失去信心
YOLO v3直接优化置信度损失,让模型学会区分图片的背景和前景区域,类似于更快的R-CNN中的RPN功能:
判定规则很简单:如果预测框和所有实际框的借条都小于一定阈值,则判定为背景。否则,它是前景(包括对象)。
分类损失
这里使用的分类损失是两个分类的交叉熵。将所有类别的分类问题归结为是否属于该类别,从而将多分类问题归结为两分类问题。这样做的优点是排除了类之间的互斥,特别是解决了多类目标重叠导致的漏检问题。
这看起来如下所示:
箱式回归损失
代码中的框回归损失如下所示:
- 边界框的大小越小,BBOX_LOSS_SCALE的值就越大。我们知道YOLO v1中的锚点在损耗中做了根部和宽度处理,这是为了削弱包围盒的大小对损失值的影响;
- RESPONSE_BBOX表示如果网格单元格包含对象,则计算边界框损失;
- 两个包围盒之间的GIoU值越大,GIoU的损失值就越小,因此网络将朝着预测盒与实际盒重叠程度较高的方向进行优化。
在我的实现中,原来的欠条损失被替换为GIOU损失。这使得检测精度提高了1%左右。GIoU的优势在于它增强了预测箱和锚箱之间的距离测量方法。
GIoU背景介绍
这是一种全新的优化包围盒的方法–GIoU(Generalized IOU)。边界框通常由左上角和右下角的坐标表示,即(x1,y1,x2,y2)。你会发现这是一个矢量。L1范数或L2范数通常可以测量向量的距离。然而,当L1和L2范数取相同的值时,检测效果有很大的不同。直接表现为预测帧的IOU值和实际检测帧的IOU值变化较大,说明L1和L2指标不能很好地反映检测效果。quite a new proposed
当L1范数和L2范数相同时,IOU和GIoU的值相差很大,这表明用L范数来度量包围盒的距离是不合适的。在这种情况下,学术界一般使用借条来计算两个包围盒之间的相似度。作者发现,使用欠条有两个缺点,使其不太适合损失函数:
- 当预测框与实际框不重合时,IOU值为0,导致优化损失函数时梯度为0,即无法优化。例如,场景A和场景B的IOU值均为0,但场景B的预测效果要好于A,因为两个包围盒之间的距离更近(L范数更小):
- 即使预测框与实际框重合且IOU值相同,检测效果也有明显差异,如下图所示:
上面三个图像的IOU=0.33,但GIOU值分别为0.33、0.24和-0.1。这表明两个边界框重叠和对齐得越好,GIOU值就越高。
GIOU计算公式:
下面是它在代码中的外观(部分来自原始代码):
模范训练
权重初始化
训练神经网络,尤其是深度神经网络所面临的一个问题是梯度消失或梯度爆炸。这意味着当我们训练深度网络时,导数或斜率有时变得非常大、非常小,甚至呈指数下降。这个时候,我们看到的损失就会变成南。假设我们正在训练这样一个极深的神经网络。为简单起见,使用激活函数g(Z)=z,并且忽略偏置参数。
首先,我们假设g(Z)=z,b[l]=0,因此对于目标输出:
这里的直观理解是:如果权重W仅略大于1或单位矩阵,则深度神经网络的输出将爆炸。如果W略小于1,则可能为0.9;网络各层的输出值将呈指数递减。这意味着正确的权重值初始化尤为重要!以下是显示这一点的简单代码:
运行上述代码后,您应该会看到下面的图表:
我们可以看到,当标准差较大(STD=>0.25)时,几乎所有的输出值都集中在-1或1附近,这表明此时神经网络存在梯度爆炸。当标准差很小时(STD=0.03和0.02),我们看到输出值迅速接近0,这表明此时神经网络的梯度已经消失。如果初始化权重的标准差过大或过小,则在训练网络时可能会出现NaN。
学习率
学习率是对性能影响最大的超参数之一。如果我们只能调整一个超参数,那么最好的选择就是学习率。在大多数情况下,学习率的选择不当会导致损失变成NaN。下图显示,如果学习速率太低,梯度下降可能会很慢。如果学习速率太大,梯度下降可能会超过最小值。它可能无法收敛,甚至发散。
由于神经网络在训练之初非常不稳定,因此要将学习率设置得很低,以保证网络能够有很好的收敛性。但是较低的学习率会使培训过程非常缓慢,所以这里我们将采用一种方式,将较低的学习率逐步提高到较高的学习率,实现网络培训的?EUROœ预热?EURO�阶段,称为预热阶段。关于热身,你可以在这张纸上读到。this paper.
但假设我们将网络培训的损失降至最低。在这种情况下,不宜总是使用较高的学习率,因为这样会使权重梯度来回振荡,很难使训练损失达到全局最小。因此,最终采用了同一篇论文中的余弦衰减法。这一阶段可以称为共识衰败阶段。我们的学习率图表如下所示:paper
预先训练的Yolo v3模型权重
当前主流的目标检测方法是基于Imagenet数据集的预训练模型提取特征,然后在CoCo数据集上进行目标检测的微调训练(如YOLO算法),称为转移学习。转移学习基于数据集的相似分布。例如,Mnist与COCO数据集分布完全不同。不需要加载COCO预培训模型。
自定义Mnist数据集的快速培训
若要测试自定义Yolo v3对象检测训练是否适合您,必须首先完成教程步骤,以确保使用原始权重进行简单检测对您有效。
当您克隆GitHub存储库时,您应该看到包含mnist图像的-uroœmnistâuro�文件夹。根据这些图像,我们使用以下命令创建MNIST培训数据:GitHub
Python mnist/make_data.py
这个make_data.py脚本以正确的格式创建训练和测试图像。此外,这还会生成一个注释文件。一行对应一个图像,格式如下:
image_Absolute_path xmin,ymin,xmax,ymax,label_index xmin2,ymin2,xmax2,ymax2,label_index2.
坐标的原点在左上角,左上角=>(xmin,ymin),右下角=>(xmax,ymax),LABEL_INDEX在[0,class_numâuro“1]范围内。我们将在下一个教程中更多地讨论这一点,在那里我将向您展示如何使用您的自定义数据训练™模型。
./yolov3/configs.py文件已针对Mnist培训进行配置。
现在,您可以训练它,然后从终端运行以下命令来评估您的模型:Python Training.py tensorboard–logdir./log
稍后转到http://localhost:6006/;,跟踪您在Tensorboard中的培训进度,您应该会看到与此类似的结果:http://localhost:6006/
训练过程完成后,您可以使用detect_mnist.py脚本测试检测:Python detect_mnist.py
然后,您应该会看到与以下内容类似的结果:
结论:
这就是本教程的™。我们学习了Yolo v3算法中的损失是如何工作的,并使用Mnist数据集训练了我们的第一个自定义对象检测器。这相对容易,因为我只用几个命令就准备了测试培训的所有文件。
在下一部分中,我将向您展示如何配置自定义对象训练的所有内容,从原始权重文件传输权重,最后使用您的类进行微调。下一期再见!
最初发表于https://pylessons.com/YOLOv3-TF2-mnisthttps://pylessons.com/YOLOv3-TF2-mnist
原创文章,作者:fendouai,如若转载,请注明出处:https://panchuang.net/2021/10/10/tensorflow-2-yolov3%e6%89%8b%e5%86%99%e5%99%a8%e6%a3%80%e6%b5%8b%e5%9f%b9%e8%ae%ad%e6%95%99%e7%a8%8b-2/