yolov3损失函数改进_YOLOv3论文解析

YOLOv3已经出来很久了,自己的文字检测也是用的YOLOv3完成的,最近一直被问到一些相关细节问题,自己不看源码也确实记不起来了,干脆就简单写下来好了。代码参考均来自于Github:keras-yolov3

一、改进

改进一:边界框的预测

yolov3的anchors和yolov2一样由聚类得到,数量由5个增加到9个。直接预测得到tx,ty,tw,th,to然后通过下面两张图的转换公式得到最后的归一化真实值(还需要乘以对应图像的H,W还原)。

其中:

xywh实际值转换公式.png

xywh对应关系.png

# 将output 转换为实际值

box_xy = (K.sigmoid(feats[..., :2]) + grid) / K.cast(grid_shape[::-1], K.dtype(feats))

box_wh = K.exp(feats[..., 2:4]) * anchors_tensor / K.cast(input_shape[::-1], K.dtype(feats))

box_confidence = K.sigmoid(feats[..., 4:5])

box_class_probs = K.sigmoid(feats[..., 5:])

改进二:类别预测

不再使用Softmax进行分类,类内竞争会损失精度,对每一类使用二分类,分类损失也使用二值交叉熵。

改进三:多尺度预测

FPN已经被证明了是非常有效的tricks,自然而然被纳入了yolov3中。其中包含三个特征图尺度,分别下采样32x,16x,8x,每个特征图上设置三种大小的anchors,对应大、中、小,每一个尺度的特征图上可以得到 N × N × [3 ∗ (4 + 1 + 80)] 的结果,分别是N x N个 gird cell ,3种尺度的anchors,x、y、w、h、confidence、80类。

改进四:特征提取器

由yolov2的darknet-19升级为darknet-53。

darknet-53.png

result.png

改进五:训练方法

作者此处引用了自己的网站主页。。。

二、具体做法和实验结果

精度.png

速度.png

三、一些尝试但是不起作用

尝试使用预测中心点x、y的偏移量和w、h的比例关系,稳定性下降,结果并不好。

尝试直接预测x、y而不是使用logistic,MAP下降。

尝试使用Focal Loss,MAP下降2%,作者也不确定原因。

尝试使用Faster-rcnn的双IOU阈值,在训练期间:iou>0.7,正例;0.3

四、损失函数

xy_loss

二值交叉熵(KL散度)

wh_loss

SSE

confidence_loss

分为obj和no_obj两种情况计算。对于obj(该检测框有对应的真实框),二值交叉熵;对于no_obj(该检测框无对应的真实框),当检测框和真实框的iou低于0.5,需要计算no_obj_confidence_loss,也是二值交叉熵。

class_loss

二值交叉熵

# 这里是一个系数,面积越小权重越高

box_loss_scale = 2 - y_true[l][...,2:3]*y_true[l][...,3:4]

xy_loss = object_mask * box_loss_scale * K.binary_crossentropy(raw_true_xy, raw_pred[...,0:2], from_logits=True)

wh_loss = object_mask * box_loss_scale * 0.5 * K.square(raw_true_wh-raw_pred[...,2:4])

confidence_loss = object_mask * K.binary_crossentropy(object_mask, raw_pred[...,4:5], from_logits=True)+ \

(1-object_mask) * K.binary_crossentropy(object_mask, raw_pred[...,4:5], from_logits=True) * ignore_mask

class_loss = object_mask * K.binary_crossentropy(true_class_probs, raw_pred[...,5:], from_logits=True)

你可能感兴趣的:(yolov3损失函数改进)