看过几篇博客和官网的介绍,总结出自己切实可行的pipline,思路如下:
第一:下载官网源码,训练测试,检测测试,如果没有问题,进行下一步。
第二:开始做满足其训练的数据,包括图像和带有标注的标准xml格式文件,这一步耗时微长一些,用到了 一下三个工具:
1、P图工具
2、生成xml文件工具
3、转换图像格式工具
第三:数据替换
1、将VOCdevkit/VOC2007中的JPEGImages和Annotations替换为以上生成数据
2、生成训练所需train.txt和val.txt文件,使用工具create_list.py
3、生成训练所需的标注txt文件,使用工具voc_label_change.py
4、将上一步生成的众多txt文件放入VOCdevkit/VOC2007/labels中
第四:修改配置文件 和源码
1、cfg/voc.data文件中:class改成1;names=data/voc.names中的内容修改成自己所训练目标物的名字,该参数用于检测出目标物体后显示其类别时用;
2、cfg/yolo_voc.cfg文件中:region层classes改成1;region层上方第一个convolution层的fileters改成(classes+coords+1)*NUM,即(1+4+1)*5=30,所以把filters改成30。
3、src/yolo.c文件中:char *voc_names的类别,改成自己的类别名字,例如 char *voc_names={“person”};draw_detection这个函数的最后一个参数改成自己所训练的类别数,比如1;demo函数中倒数第三个参数从20改成1。
4、src/detector里面的路径,可选择性修改。
第五:训练:./darknet detector train cfg/voc.data cfg/yolo-voc.cfg darknet19_448.conv.23,最后参数保存在backup中。
第六:测试:./darknet detector test cfg/voc.data cfg/yolo-voc.cfg yolo_voc_final.weights test/*.jpg -thresh 0.08
经过漫长的训练过程,model终于训练好了,为了评估性能,可以使用以下指令
./darknet detector recall cfg/voc.data cfg/yolo_voc.cfg backup/yolo_voc_final.weights
需要注意的是,在使用这个指令之前,我先修改一下src/detector.c 这一函数
fprintf(stderr, "ID:%5d Correct:%5d Total:%5d\tRPs/Img: %.2f\tIOU: %.2f%%\tRecall:%.2f%%\t", i, correct, total, (float)proposals/(i+1), avg_iou*100/total, 100.*correct/total);
fprintf(stderr, "proposals:%5d\tPrecision:%.2f%%\n",proposals,100.*correct/(float)proposals);
运行后显示的结果是:
…..
ID: 101 Correct: 106 Total: 111 RPs/Img: 1.07 IOU: 82.00% Recall:95.50% proposals: 109 Precision:97.25%
ID: 102 Correct: 107 Total: 112 RPs/Img: 1.07 IOU: 82.11% Recall:95.54% proposals: 110 Precision:97.27%
结果中的参数,理解:
Correct :可以理解为正确地画了多少个框,遍历每张图片的Ground Truth,网络会预测出很多的框,对每一Groud Truth框与所有预测出的框计算IoU,在所有IoU中找一个最大值,如果最大值超过一个预设的阈值,则correct加一。
Total:一共有多少个Groud Truth框。
Rps/img:p 代表proposals, r 代表region。 意思就是平均下来每个图片会有预测出多少个框。预测框的决定条件是,预测某一类的概率大于阈值。在validation_yolo_recall函数中,默认的这一个阈值是0.001,这一阈值设置的比较低,这就会导致会预测出很多个框,但是这样做是可以提升recall的值,一般yolo用于画框的默认值是.25,使用这个阈值会让画出来的框比较准确。而validation_yolo_recall使用的阈值改成。25的时候,Rps/img 值会降低,recall的值会降低,所以validation_yolo_recall默认使用一个较低的阈值,有可能作者的目的就是为了提高recall值,想在某种程度上体现网络的识别精度比较高。
IoU、Recall、Precision:解释起来比较麻烦,请看我的博客有详细说明:
http://blog.csdn.net/hysteric314/article/details/54093734