train yolov3

这些天在复现YOLOV3时,训练过程中遇到了一些问题,在这里记录一下跑网络的过程~


训练指令

注意根据情况修改Makefile文件,并重新make,以及cfg文件夹下yolov3-voc.cfg文件,在darknet目录下执行命令:

格式:./darknet detector train [data_cfg] [network_cfg] [weight] -gpus [gpu_nums]

CPU上训练

./darknet -ngpu detector train cfg/voc.data cfg/yolov3-voc.cfg darknet.conv.74

多GPU训练

./darknet detector train cfg/voc.data cfg/yolov3-voc.cfg darknet.conv.74 -gpus 0,1

输出重定向

如果需要将训练过程可视化,则训练时将输出重定向得到训练日志文件;

./darknet detector train cfg/voc.data cfg/yolov3-voc.cfg darknet.conv.74 -gpus 0,1 2>1 | tee train_yolov3.log

从检查点开始恢复训练

./darknet detector train cfg/voc.data cfg/yolov3-voc.cfg backup/yolov3.backup -gpus 0,1


输出解释

forward_yolo_layer()

每个子batch输出一次,详见src文件夹下yolo_layer.c文件的forward_yolo_layer函数。

1
printf("Region %d Avg IOU: %f, Class: %f, Obj: %f, No Obj: %f, .5R: %f, .75R: %f,  count: %d\n", net.index, avg_iou/count, avg_cat/class_count, avg_obj/count, avg_anyobj/(l.w*l.h*l.n*l.batch), recall/count, recall75/count, count);
  • Region [xx]: cfg文件中的layer的索引;

  • Avg IOU: 当前迭代过程中,预测的bbox和ground truth的平均交并比,理想值为1;

  • Class: 标注物体的分类准确率,理想值为1;

  • Obj: 期望该值越接近1越好;

  • No Obj: 期望该值越小越好;

  • .5R: IoU=0.5为阈值时,当前子batch中recall值;

  • .75R: IoU=0.75为阈值时,当前子batch中recall值;

  • count: 当前subdivision的子batch中所有图片中包含的正样本数。count = 0表示该批次该尺度上没有检测到对象,会导致Avg IOUClassobj.5R.75R值均为-nannan。这可能是由于在许多小物体上训练导致的,所以在显存允许的情况下,可适当增大batch的大小,可一定程度减少nan的出现。

train_detector()

每个batch输出一次loss,详见examples文件夹下detect.c文件中train_detector函数:

1
printf("%ld: %f, %f avg, %f rate, %lf seconds, %d images\n", get_current_batch(net), loss, avg_loss, get_current_rate(net), what_time_is_it_now()-time, i*imgs);

问题及解决

CUDA: out of memory

显存不够引起的,修改yolov3-voc.cfg文件。

  • 修改[net]层参数,增大subdivisions或调小batch,因为训练时实际每次前向的图片数量 = batch/subdivisions。

  • 关闭多尺度训练。将所有[yolo]层中random参数修改为random = 0


参数调整

  1. Batch_Size:想要模型快速收敛,最好是增大Batch_Size,但可能导致陷入局部最小的情况;减小Batch_Size可能会有更好的效果,但是如果类别数较多,Batch_Size又太小,会导致loss函数震荡不收敛。一般在调试时,根据GPU显存,设置为最大(一般要求为8的倍数),选部分数据跑几个Batch看看loss是否在变小,再选择合适的值。yolov3-voc.cfg文件中对应参数为batch

  2. 如果内存不够大,增大subdivision值,将batch分割,每个子batch大小为 batch/subdivisions。

  3. 为了应对小目标检测,网络输入大一些更好,即增大weightheight

  4. random = 1会使用多尺度训练,随机使用不同尺寸的图片进行训练;如果为0,则每次训练图片大小与输入尺寸一致。

------ Finished ------
0%