作者:欧新宇(Xinyu OU)
当前版本:Release v1.0
开发平台:Paddle 2.3.2
运行环境:Intel Core i7-7700K CPU 4.2GHz, nVidia GeForce GTX 1080 Ti
本教案所涉及的数据集仅用于教学和交流使用,请勿用作商用。
最后更新:2025年1月30日
垃圾分类数据集Garbage 是一个包含有40个类别,14802张图像的数据集。该数据集已经事先实现了训练(train)
和测试(test)
的分割,其中测试集没有类别标签。数据集没有给出验证集的划分建议,因此在进行数据列表生成的时候,可以自行按照一定的比列来将官方提供的训练集看作是trainval进行二次划分,即将原来的 train
文件夹划分为训练集train和验证集val。使用train和val完成训练之后,再按照训练获得超参数,对整个训练验证集trainval进行训练,完成后直接输出 测试集结果
到平台进行评估。注意,本数据集给出了类别的标签字典,因此在生成和划分数据子集的时候,建议考虑基于该类别标签字典而非遍历文件夹的方式来完成。
以下代码为本项目完整代码,可以直接/拷贝至Python文件中运行。在以下代码中去除了部分用于分析用的 print
语句。
# pcodes00301_data_preparation ################################################################################## # 数据集预处理 # 作者: Xinyu Ou (http://ouxinyu.cn) # 数据集名称:垃圾分类数据集Garbage # 数据集简介: 数据集包含40个类别,其中训练样本14402张,测试样本400张。 # 本程序功能: # 1. 在训练集中抽取10%的样本作为验证数据集 # 2. 代码将生成4个带标注的列表文件:train, val, trainval, test # 3. 数据集基本信息:数据集的基本信息使用json格式进行输出,包括数据库名称、数据样本的数量、类别数以及类别标签 ################################################################################### import os import json import codecs ######################################################### # 1. 超参数的初始化 [Q1-1] # [Your codes 1] num_train = 0 num_val = 0 num_trainval = 0 num_test = 0 class_dim = 0 dataset_info = { 'dataset_name': '', 'num_trainval': -1, 'num_train': -1, 'num_val': -1, 'num_test': -1, 'class_dim': -1, 'label_dict': {} } # 设置图片的前缀,即图像根目录下的子目录路径 train_prefix = 'train' # train_prefix = val_prefix = trainval_prefix test_prefix = 'test' ######################################################### # 2. 数据集相关路径定义。本地运行时,需要修改数据集的名称和绝对路径,注意和文件夹名称一致。 # 2.1 数据集源路径定义 dataset_name = 'Garbage' # 1. Windows # root_path = 'D:\\Workspace\\ExpDatasets'' # 2. aistudio root_path = '/home/aistudio/work' dataset_root_path = os.path.join(root_path, dataset_name) exclusion = ['.DS_Store', '.ipynb_checkpoints'] # 被排除的文件夹 # 2.2 数据集输出路径定义 [Q2-1] # [Your codes 2] trainval_list = os.path.join(dataset_root_path, 'trainval.txt') train_list = os.path.join(dataset_root_path, 'train.txt') val_list = os.path.join(dataset_root_path, 'val.txt') test_list = os.path.join(dataset_root_path, 'test.txt') dataset_info_list = os.path.join(dataset_root_path, 'dataset_info.json') garbage_dict_path = os.path.join(dataset_root_path, 'garbage_dict.json') # 2.3 检测数据集列表是否已经存在,如果存在则先删除。 # 在Garbage数据集中,测试集只需要一次性写入,可以通过'w'参数进行覆盖写入,而不用进行手动删除。 if os.path.exists(train_list): os.remove(train_list) if os.path.exists(val_list): os.remove(val_list) if os.path.exists(trainval_list): os.remove(trainval_list) if os.path.exists(dataset_info_list): os.remove(dataset_info_list) # 2.4 从官方文件garbage_dict.json获取类别标签 with open(garbage_dict_path, 'r', encoding='utf-8') as f_dict: garbage_dict = json.load(f_dict) # 2.5 读取数据清洗获得的坏样本列表,并将坏文件写入列表以备后续排除(本例可忽略) ######################################################### # 3. 生成四个不同的数据子集列表 # 3.1 生成测试集列表 [Q3-1] # 特别注意,因测试集的输出结果需要使用专门的系统进行评估(AIStudio),因此测试集样本列表需要对文件严格按照数字从小到大进行排序 # [Your codes 3] testImg_list = os.listdir(os.path.join(dataset_root_path, test_prefix)) test_numbers = [] for testImg in testImg_list: if testImg not in exclusion: test_name = testImg.split('.') # 拆分文件名和扩展名 test_numbers.append(int(test_name[0][4:])) # 获取文件名中的数字部分 test_numbers.sort() # 对测试文件,按照数字序号进行排序 num_test = len(test_numbers) with codecs.open(test_list, 'w', 'utf-8') as f_test: for i in test_numbers: # 按照序号列表遍历测试数据,并生成测试文件列表 image_path = os.path.join(dataset_root_path, test_prefix, 'test' + str(i) + '.jpg') f_test.write('{}\n'.format(image_path)) # 3.2 生成训练集、验证集和训练验证集列表 [Q3-2] # [Your codes 4] labelID_list = list(garbage_dict.keys()) with codecs.open(train_list, 'a', 'utf-8') as f_train, codecs.open(val_list, 'a', 'utf-8') as f_val, codecs.open(trainval_list, 'a', 'utf-8') as f_trainval: for label_id in labelID_list: trainImgs = os.listdir(os.path.join(dataset_root_path, train_prefix, label_id)) count = 0 for trainImg in trainImgs: if trainImg not in exclusion: image_path = os.path.join(dataset_root_path, train_prefix, label_id, trainImg) if count % 10 == 0: # 抽取大约10%的样本作为验证数据 f_val.write("{}\t{}\n".format(image_path, label_id)) f_trainval.write("{}\t{}\n".format(image_path, label_id)) num_val += 1 num_trainval += 1 else: f_train.write("{}\t{}\n".format(image_path, label_id)) f_trainval.write("{}\t{}\n".format(image_path, label_id)) num_train += 1 num_trainval += 1 count += 1 ######################################################### # 4. 输出统计结果 # 4.1 将数据集信息保存到json文件中供训练和部署使用 [Q4-1] # 数据集信息包括:数据集名称,训练、验证、测试及训练验证集的样本数量、类别的数量和类别字典 # [Your codes 5] dataset_info['dataset_name'] = dataset_name dataset_info['num_trainval'] = num_trainval dataset_info['num_train'] = num_train dataset_info['num_val'] = num_val dataset_info['num_test'] = num_test dataset_info['class_dim'] = len(garbage_dict) dataset_info['label_dict'] = garbage_dict # 4.2.输出数据集信息到json文件 with codecs.open(dataset_info_list, 'w', encoding='utf-8') as f_dataset_info: json.dump(dataset_info, f_dataset_info, ensure_ascii=False, indent=4, separators=(',', ':')) # 格式化字典格式的参数列表 # 4.3 在控制台中打印数据集基本统计信息 [Q4-2] # 注意为方便可视化,考虑使用display()替代print()对字典进行输出,但display()只支持notebook接口。 # [Your codes 6] print("图像列表已生成, 其中训练验证集样本{},训练集样本{}个, 验证集样本{}个, 测试集样本{}个, 共计{}个。".format(num_trainval, num_train, num_val, num_test, num_train+num_val+num_test)) display(dataset_info)
图像列表已生成, 其中训练验证集样本14402,训练集样本12944个, 验证集样本1458个, 测试集样本400个, 共计14802个。
{'dataset_name': 'Garbage',
'num_trainval': 14402,
'num_train': 12944,
'num_val': 1458,
'num_test': 400,
'class_dim': 40,
'label_dict': {'0': '其他垃圾/一次性快餐盒',
'1': '其他垃圾/污损塑料',
'2': '其他垃圾/烟蒂',
'3': '其他垃圾/牙签',
'4': '其他垃圾/破碎花盆及碟碗',
'5': '其他垃圾/竹筷',
'6': '厨余垃圾/剩饭剩菜',
'7': '厨余垃圾/大骨头',
'8': '厨余垃圾/水果果皮',
'9': '厨余垃圾/水果果肉',
'10': '厨余垃圾/茶叶渣',
'11': '厨余垃圾/菜叶菜根',
'12': '厨余垃圾/蛋壳',
'13': '厨余垃圾/鱼骨',
'14': '可回收物/充电宝',
'15': '可回收物/包',
'16': '可回收物/化妆品瓶',
'17': '可回收物/塑料玩具',
'18': '可回收物/塑料碗盆',
'19': '可回收物/塑料衣架',
'20': '可回收物/快递纸袋',
'21': '可回收物/插头电线',
'22': '可回收物/旧衣服',
'23': '可回收物/易拉罐',
'24': '可回收物/枕头',
'25': '可回收物/毛绒玩具',
'26': '可回收物/洗发水瓶',
'27': '可回收物/玻璃杯',
'28': '可回收物/皮鞋',
'29': '可回收物/砧板',
'30': '可回收物/纸板箱',
'31': '可回收物/调料瓶',
'32': '可回收物/酒瓶',
'33': '可回收物/金属食品罐',
'34': '可回收物/锅',
'35': '可回收物/食用油桶',
'36': '可回收物/饮料瓶',
'37': '有害垃圾/干电池',
'38': '有害垃圾/软膏',
'39': '有害垃圾/过期药物'}}