YOLOv2代码分析_读取labels[by zhangzexuan]

本文详细分析了YOLOv2的代码,特别是关于如何读取ground-truth标签的部分。从YOLOv2的输入材料到代码的逐层深入,揭示了如何从图片路径获取对应的标签文档,以及数据加载流程的关键步骤。通过理解这些,有助于进一步修改YOLOv2以适应新的需求,如同时预测人脸和特征点。
摘要由CSDN通过智能技术生成

YOLOv2代码分析_读取labels[by zhangzexuan]

嗯……现在参与的项目要求在人脸检测步骤直接连同人脸特征点一起预测出来,因此需要我做标题说明的工作,但是看了很久的YOLOv2代码也没有什么头绪,初步的想法是需要修改以下几个地方的代码:

  • 读取ground-truth标签文档
  • 损失函数
  • 非极大值抑制

但是YOLOv2的代码我读了好几天,都没有找到在什么地方读取的ground-truth标签,就决定把看到的想到的东西记录下来,慢慢研究,好记性不如烂笔头嘛。


YOLOv2的输入

yolov2在训练的时候需要输入的材料如下:
- .data文件,其中记录了检测类别数,训练集图片路径文档路径,验证集图片路径文档路径,类别名文件路径,权重文件存储路径
- 训练集图片路径文档
- 验证集图片路径文档
- 类别名文件
- ground-truth标签文档

由以上可以看出.data 文件指示了图片地址但没有指示labels的地址,那么yolo是如何找到labels文档的呢。其实这里yolo使用的是标准voc数据格式,数据的部署采用voc的目录结构,那么知道了图片地址,就可以在图片路径的上级目录中的labels子目录下找到所有的label文档。当然这些肯定是在代码中实现的了,要想找到读取label文档的代码,那么首先就是要找到读取.data文件的代码,看看代码是在什么地方通过图片路径去寻找label文档的。

代码阅读

在detector.c的最后部分,函数run_detector对终端指令参数进行分析,指示train参数转到函数train_detector,因此接下来我们主要看的就是train_detector的内容。

//detector.c[5-9]
void train_detector(char *datacfg, char *cfgfile, char *weightfile, int *gpus, int ngpus, int clear)
{
    list *options = read_data_cfg(datacfg);
    char *train_images = option_find_str(options, "train", "data/train.list");
    char *backup_directory = option_find_str(options, "backup", "/backup/");

上面是函数train_detector的头三行代码,参数datacfg就是终端命令参数中的.data文件路径,read_data_cfg()将.data的内容读取出来存储在一个名为options的list类型变量中,option_find_str()将options变量中的关键词为train的内容读取到字符串train_images中,就是说字符串train_images的内容为训练图片路径文档的路径。

//detector.c[40-46]
    list *plist = get_paths(train_images);
    //int N = plist->size;
    char **paths = (char **)list_to_array(plist);

    load_args args = get_base_args(net);
    args.coords = l.coords;
    args.paths = paths;

这里get_paths()通过train_images中存储的路径将训练图片路径文档中的每一行都存入一个字符串中,然后将每个字符串地址存入一个node结构体中,并返回一个list结构体指针,这个list结构体中包含指向第一个和最后一个node结构体的指针。总的来说就是把所有的图片路径都存进一个链表中,list结构体中的指针分别指向这个链表的头结点和尾结点。
函数list_ro_array()只是单纯将存在list中的图片路径全部存入到字符串数组paths中去。
可以看到paths的值又被赋给了args.paths,接下来我们看args.paths的动向。

//detector.c[57-84]
    pthread_t load_thread = load_data(args);
    clock_t time;
    int count = 0;
    //while(i*imgs < N*120){
   
    while(get_current_batch(net) < net.max_batches){
        if(l.random && count++%10 == 0){
            printf("Resizing\n");
            int dim = (rand() % 10 + 10) * 32;
            if (get_current_batch(net)+200 > net.max_batches) dim = 608;
            //int dim = (rand() % 4 + 16) * 32;
            printf("%d\n", dim);
            args.w = dim;
            args.h = dim;

            pthread_join(load_thread, 0);
            train = buffer;
            free_data(train);
            load_thread = load_data(args);

            for(i =
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值