使用PaddleDetection框架对自定义训练集进行训练和测试(1)

本文旨在记录使用PaddleDetection框架对自定义数据集进行训练的流程

环境准备

使用Ai Studio提供的项目环境,由下列代码对环境进行安装

	cd work
	git clone https://github.com/PaddlePaddle/PaddleDetection.git # 安装其他依赖
	cd PaddleDetection
	pip install -r requirements.txt
	python setup.py install

如果太慢的话可以挂梯子,或者使用gitee

  git clone https://github.com/PaddlePaddle/PaddleDetection.git

数据集准备

我们使用AI识虫数据集进行训练,由于本文使用PPYOLOE模型对数据集进行训练和预测,而PPYOLOE模型目前只接受COCO类型的数据集,所以首先需要对数据集进行转换,转换后的数据集再文末会提供。
从Paddle其他用户分享的VOC类型的AI识虫数据集的文件目录如下:

	├─Annotations
	│  ├─test
	│  ├─train
	│  └─val
	├─ImageSets
	│  ├─test.txt
	│  ├─train.txt
	│  ├─val.txt
	│  └─label_list.txt
	└─JPEGImages
	    ├─test
	    ├─train
	    └─val

Annotations存储着XML文件,ImageSets存储着train.txt,val.txt,test.val以及label_list.txt(这四个文件很重要,因为在转换成coco数据集时,需要这四个文件)。JPEGImages存储着数据集的图片。这是一个比较标准的VOC格式的数据集,可惜PPYOLOE不能使用。转换后的COCO数据集是这样的,由于我们暂时不需要测试集,所以把测试集去掉了。可以看到,txt文件不见了,取而代之的是json文件。同样的,images下存着是train和val的文件。

├─annotations
	│  ├─train.json
	│  └─val.json
└─images
    ├─train
    └─val

对数据集进行转换

使用官方的转换方法对数据集进行转换,下面是官方教程

https://gitee.com/paddlepaddle/PaddleDetection/blob/release/2.5/docs/tutorials/data/PrepareDetDataSet.md

官方的代码如下:

python tools/x2coco.py \
        --dataset_type voc \
        --voc_anno_dir path/to/VOCdevkit/VOC2007/Annotations/ \
        # --voc_anno代表你annotations所在的路径
        # path/to 代表根路径,就是要把路径从头到尾写全。
        --voc_anno_list path/to/VOCdevkit/VOC2007/ImageSets/Main/trainval.txt \
        # voc_anno_list 需要你的txt文件作为参数,因为要根据你的txt文件的内容来编写json文件
        --voc_label_list dataset/voc/label_list.txt \
        # label_list文件,需要知道数据集有多少类别
        --voc_out_name voc_train.json
        #输出文件名

下面是我的转换代码

python ~/work/PaddleDetection/tools/x2coco.py \
       --dataset_type voc \
       --voc_anno_dir ~/work/PaddleDetection/dataset/voc/insect/Annotations/train \
       --voc_anno_list  ~/work/PaddleDetection/dataset/voc/insect//ImageSets/train.txt \
       --voc_label_list ~/work/PaddleDetection/dataset/voc/insect/ImageSets/label_list.txt \
       --voc_out_name  train.json
python ~/work/PaddleDetection/tools/x2coco.py \
        --dataset_type voc \
        --voc_anno_dir ~/work/PaddleDetection/dataset/voc/insect/Annotations/val \
        #需要对train和val一起转换,所以要转换两次,一次是train,一次是val
        --voc_anno_list  ~/work/PaddleDetection/dataset/voc/insect//ImageSets/val.txt \
        --voc_label_list ~/work/PaddleDetection/dataset/voc/insect/ImageSets/label_list.txt \
        --voc_out_name  val.json

注意,直接使用上述代码会报错,因为其他用户提供的txt文件中的内容是存在问题的,如下所示,这是原本的txt文件的内容:

../JPEGImages/train/10.jpeg ../Annotations/train/10.xml
../JPEGImages/train/10.jpeg ../Annotations/train/10.xml
../JPEGImages/train/10.jpeg ../Annotations/train/10.xml
../JPEGImages/train/10.jpeg ../Annotations/train/10.xml
../JPEGImages/train/104.jpeg ../Annotations/train/104.xml
../JPEGImages/train/104.jpeg ../Annotations/train/104.xml
../JPEGImages/train/104.jpeg ../Annotations/train/104.xml
...

由于官方的工具会尝试读取

../Annotations/train/10.xml

作为参数进行json转换,而这种格式不符合官方工具所需要的数据格式,所以需要重新生成txt文件,把txt文件改成如下所示:

10
104
...

10对应10.xml,104对应104.xml,下面给出python代码。

import os
from glob import glob
from sklearn.model_selection import train_test_split

# 1.标签路径

saved_path = "C:/Users/Kyon/Pictures/Downloads/insect2/insect"  # 保存路径

# 2.创建要求文件夹,如果不存在ImageSets/Main,那么就生成
if not os.path.exists(saved_path + "ImageSets/Main/"):
    os.makedirs(saved_path + "ImageSets/Main/")


# 3.split files for txt, Python open + 'w'如果文件不存在,则生成一个
txtsavepath = saved_path + "ImageSets/Main/"
ftrainval = open(txtsavepath + '/trainval.txt', 'w')
ftrain = open(txtsavepath + '/train.txt', 'w')
fval = open(txtsavepath + '/val.txt', 'w')
ftest = open(txtsavepath + '/val.txt', 'w')

total_files_train = glob(saved_path + "/Annotations/train/*.xml")
total_files_val=glob(saved_path + "/Annotations/val/*.xml")
total_files_test=glob(saved_path + "/Annotations/test/*.xml")


# 分别截取xml文件名
total_files_train = [i.split("\\")[-1].split('.xml')[0] for i in total_files_train]

total_files_val = [i.split("\\")[-1].split('.xml')[0] for i in total_files_val]

total_files_test=[i.split("\\")[-1].split('.xml')[0] for i in total_files_val]

print(total_files_train)
#
# for file in total_files:
#     ftrainval.write(file + "\n")
#
# # split
# train_files, val_files = train_test_split(total_files, test_size=0.15, random_state=42)
#
# train
for file in total_files_train:
    ftrain.write(file + "\n")
# val
for file in total_files_val:
     fval.write(file + "\n")

#
# ftrainval.close()
# ftrain.close()
# fval.close()
#

于是乎,你会得到train.txt和val.txt文件,把这两个文件上传到你的项目中去,再用上面的转换代码转换出Json文件,并按VOC文件格式把Json文件和图片整理好,最终效果如下所示:

├── annotations
└── images
    ├── train
    └── val

训练配置

在下述路径中找到配置数据集路径的配置文件

/home/aistudio/work/PaddleDetection/configs/datasets/coco_detection.yml

修改训练集和验证集的路径,其中image_dir和anno_path的路径都是相对于dataset_dir的,而dataset_dir无需写全路径(也许是系统默认所在路径?)

metric: COCO
num_classes: 80

TrainDataset:
  !COCODataSet
    image_dir: images/train
    anno_path: annotations/train.json
    dataset_dir: dataset/insects
    data_fields: ['image', 'gt_bbox', 'gt_class', 'is_crowd']

EvalDataset:
  !COCODataSet
    image_dir: images/val
    anno_path: annotations/val.json
    dataset_dir: dataset/insects

TestDataset:
  !ImageFolder
    anno_path: annotations/instances_val2017.json # also support txt (like VOC's label_list.txt)
    dataset_dir: dataset/coco # if set, anno_path will be 'dataset_dir/anno_path'
···

数据处理好后就可以开启训练啦!具体的训练配置以后再说

你可能感兴趣的:(深度学习与Paddle,python,开发语言,深度学习,paddlepaddle)