整个实现过程所涉及的文件目录,其中,自备表示自己需要准备的,生成表示无需自己准备。
使用yolov5时出现“assertionerror:no labels found in */*/*/JPEGImages.cache can not train without labels”问题
很多朋友都会遇到的一个问题,yolo5-6.1已经不能使用之前的方法了了,是下载源码后的coco示例。
- nvidia@nvidia-desktop:~/works/yolov5-6.1$ cat data/coco128.yaml
- # YOLOv5 🚀 by Ultralytics, GPL-3.0 license
- # COCO128 dataset https://www.kaggle.com/ultralytics/coco128 (first 128 images from COCO train2017) by Ultralytics
- # Example usage: python train.py --data coco128.yaml
- # parent
- # ├── yolov5
- # └── datasets
- # └── coco128 ← downloads here
-
-
- # Train/val/test sets as 1) dir: path/to/imgs, 2) file: path/to/imgs.txt, or 3) list: [path/to/imgs1, path/to/imgs2, ..]
- path: ../datasets/coco128 # dataset root dir
- train: images/train2017 # train images (relative to 'path') 128 images
- val: images/train2017 # val images (relative to 'path') 128 images
- test: # test images (optional)
-
- # Classes
- nc: 80 # number of classes
- names: ['person', 'bicycle', 'car', 'motorcycle', 'airplane', 'bus', 'train', 'truck', 'boat', 'traffic light',
- 'fire hydrant', 'stop sign', 'parking meter', 'bench', 'bird', 'cat', 'dog', 'horse', 'sheep', 'cow',
- 'elephant', 'bear', 'zebra', 'giraffe', 'backpack', 'umbrella', 'handbag', 'tie', 'suitcase', 'frisbee',
- 'skis', 'snowboard', 'sports ball', 'kite', 'baseball bat', 'baseball glove', 'skateboard', 'surfboard',
- 'tennis racket', 'bottle', 'wine glass', 'cup', 'fork', 'knife', 'spoon', 'bowl', 'banana', 'apple',
- 'sandwich', 'orange', 'broccoli', 'carrot', 'hot dog', 'pizza', 'donut', 'cake', 'chair', 'couch',
- 'potted plant', 'bed', 'dining table', 'toilet', 'tv', 'laptop', 'mouse', 'remote', 'keyboard', 'cell phone',
- 'microwave', 'oven', 'toaster', 'sink', 'refrigerator', 'book', 'clock', 'vase', 'scissors', 'teddy bear',
- 'hair drier', 'toothbrush'] # class names
-
-
- # Download script/URL (optional)
| 检测目标 | 类型 | 标注工具 | 标注格式 | 训练工具 |
|---|---|---|---|---|
| 笔 | "open" | labelimg | pascalVOC | YOLO5 |
整个实现过程所涉及的文件目录,其中,自备表示自己需要准备的,生成表示无需自己准备。
首先录取视频获取图片,在d盘下创建目录dataSet,然后再dataSet内分别创建目录images、和video目录,如下:
- import cv2
- import os.path
- import random
-
-
- # 检查已有图片的数量,确定本次图片抽取开始的下标
- cnt = len(os.listdir('D:/dataSet/images')) + 1
- # 视频存放路径
- videoDir = os.listdir('D:/dataSet/video')
- # 提示使用者抽取开始
- print("Start!")
- # 每30帧随机抽取一帧
- start, ran = 0, random.randrange(0, 30)
- try:
- temp = 0
- for video in videoDir:
- # 拼接视频路径
- videoPath = r'D:/dataSet/video/' + video
-
- # 打开视频流
- vc = cv2.VideoCapture(videoPath)
- # 判断是否打开成功
- if vc.isOpened():
- while True:
- # activity: 读取成功标签,frame: 读取的画面
- activity, frame = vc.read()
- # 如果读取不成功(没有下一帧),就退出
- if not activity:
- break
- if temp == start + ran:
- cv2.imwrite(f"D:/VOCdevkit/VOC2007/PEGImages/{cnt}.jpg", frame)#这里的路径是提前建好的
- cnt, start, ran = cnt + 1, start + 30, random.randrange(0, 30)
- temp = temp + 1
- vc.release()
- # 提示抽取完成
- print("Finish!")
- except:
- vc.release()
- # 提示抽取出现错误
- print("Error!")

内容为空 。
在cmd窗口进入d盘,输入命令:
python manage.py
出现“Finish!”即为抽取完成,效果如下:

完成前面的工作后,在控制台输入labelimg:



最终目录架构,test的目录不是必须的,现在的版本是没用到
- D:\VOCdevkit>tree
- 卷 DATA1 的文件夹 PATH 列表
- 卷序列号为 141F-A5EC
- D:.
- ├─images
- │ ├─test
- │ ├─train
- │ └─val
- ├─labels
- │ ├─test
- │ ├─train
- │ └─val
- └─VOC2007
- ├─Annotations
- ├─PEGImages
- └─YOLOLabels
使用图如下代码即可将标注的文件.xml格式文件转为.txt格式
- import xml.etree.ElementTree as ET
- import pickle
- import os
- from os import listdir, getcwd
- from os.path import join
- import random
- from shutil import copyfile
-
- # 根据自己的数据标签修改
- classes=["pen", "pen"]
-
-
- def clear_hidden_files(path):
- dir_list = os.listdir(path)
- for i in dir_list:
- abspath = os.path.join(os.path.abspath(path), i)
- if os.path.isfile(abspath):
- if i.startswith("._"):
- os.remove(abspath)
- else:
- clear_hidden_files(abspath)
-
- def convert(size, box):
- dw = 1./size[0]
- dh = 1./size[1]
- x = (box[0] + box[1])/2.0
- y = (box[2] + box[3])/2.0
- w = box[1] - box[0]
- h = box[3] - box[2]
- x = x*dw
- w = w*dw
- y = y*dh
- h = h*dh
- return (x,y,w,h)
-
- def convert_annotation(image_id):
- in_file = open('D:/VOCdevkit/VOC2007/Annotations/%s.xml' % image_id, encoding='UTF-8' )
- out_file = open('D:/VOCdevkit/VOC2007/YOLOLabels/%s.txt' % image_id, 'w')
- tree=ET.parse(in_file)
- root = tree.getroot()
- size = root.find('size')
- w = int(size.find('width').text)
- h = int(size.find('height').text)
-
- for obj in root.iter('object'):
- difficult = obj.find('difficult').text
- cls = obj.find('name').text
- if cls not in classes or int(difficult) == 1:
- continue
- cls_id = classes.index(cls)
- xmlbox = obj.find('bndbox')
- b = (float(xmlbox.find('xmin').text), float(xmlbox.find('xmax').text), float(xmlbox.find('ymin').text), float(xmlbox.find('ymax').text))
- bb = convert((w,h), b)
- out_file.write(str(cls_id) + " " + " ".join([str(a) for a in bb]) + '\n')
- in_file.close()
- out_file.close()
-
- wd = os.getcwd()
- wd = os.getcwd()
- data_base_dir = os.path.join(wd, 'D:/VOCdevkit/')
- if not os.path.isdir(data_base_dir):
- os.mkdir(data_base_dir)
- work_sapce_dir = os.path.join(data_base_dir, 'D:/VOCdevkit/VOC2007/')
- if not os.path.isdir(work_sapce_dir):
- os.mkdir(work_sapce_dir)
- annotation_dir = os.path.join(work_sapce_dir, 'D:/VOCdevkit/VOC2007/Annotations/')
- if not os.path.isdir(annotation_dir):
- os.mkdir(annotation_dir)
- clear_hidden_files(annotation_dir)
- image_dir = os.path.join(work_sapce_dir, 'D:/VOCdevkit/VOC2007/PEGImages/')
- if not os.path.isdir(image_dir):
- os.mkdir(image_dir)
- clear_hidden_files(image_dir)
- yolo_labels_dir = os.path.join(work_sapce_dir, 'D:/VOCdevkit/VOC2007/YOLOLabels/')
- if not os.path.isdir(yolo_labels_dir):
- os.mkdir(yolo_labels_dir)
- clear_hidden_files(yolo_labels_dir)
- yolov5_images_dir = os.path.join(data_base_dir, 'images/')
- if not os.path.isdir(yolov5_images_dir):
- os.mkdir(yolov5_images_dir)
- clear_hidden_files(yolov5_images_dir)
- yolov5_labels_dir = os.path.join(data_base_dir, 'labels/')
- if not os.path.isdir(yolov5_labels_dir):
- os.mkdir(yolov5_labels_dir)
- clear_hidden_files(yolov5_labels_dir)
-
-
- yolov5_images_train_dir = os.path.join(yolov5_images_dir, 'train/')
- if not os.path.isdir(yolov5_images_train_dir):
- os.mkdir(yolov5_images_train_dir)
- clear_hidden_files(yolov5_images_train_dir)
- yolov5_images_test_dir = os.path.join(yolov5_images_dir, 'val/')
- if not os.path.isdir(yolov5_images_test_dir):
- os.mkdir(yolov5_images_test_dir)
- clear_hidden_files(yolov5_images_test_dir)
- yolov5_images_val_dir = os.path.join(yolov5_images_dir, 'test/')
- if not os.path.isdir(yolov5_images_val_dir):
- os.mkdir(yolov5_images_val_dir)
- clear_hidden_files(yolov5_images_val_dir)
- yolov5_labels_train_dir = os.path.join(yolov5_labels_dir, 'train/')
- if not os.path.isdir(yolov5_labels_train_dir):
- os.mkdir(yolov5_labels_train_dir)
- clear_hidden_files(yolov5_labels_train_dir)
- yolov5_labels_test_dir = os.path.join(yolov5_labels_dir, 'val/')
- if not os.path.isdir(yolov5_labels_test_dir):
- os.mkdir(yolov5_labels_test_dir)
- clear_hidden_files(yolov5_labels_test_dir)
- yolov5_labels_val_dir = os.path.join(yolov5_labels_dir, 'test/')
- if not os.path.isdir(yolov5_labels_val_dir):
- os.mkdir(yolov5_labels_val_dir)
- clear_hidden_files(yolov5_labels_val_dir)
-
- train_file = open(os.path.join(wd, 'yolov5_train.txt'), 'w')
- test_file = open(os.path.join(wd, 'yolov5_val.txt'), 'w')
- val_file = open(os.path.join(wd, 'yolov5_tes.txt'), 'w')
- train_file.close()
- test_file.close()
- val_file.close()
- train_file = open(os.path.join(wd, 'yolov5_train.txt'), 'a')
- test_file = open(os.path.join(wd, 'yolov5_val.txt'), 'a')
- val_file = open(os.path.join(wd, 'yolov5_test.txt'), 'a')
- list_imgs = os.listdir(image_dir) # list image files
- probo = random.randint(1, 100)
- print("Probobility: %d" % probo)
- for i in range(0,len(list_imgs)):
- path = os.path.join(image_dir,list_imgs[i])
- if os.path.isfile(path):
- image_path = image_dir + list_imgs[i]
- voc_path = list_imgs[i]
- (nameWithoutExtention, extention) = os.path.splitext(os.path.basename(image_path))
- (voc_nameWithoutExtention, voc_extention) = os.path.splitext(os.path.basename(voc_path))
- annotation_name = nameWithoutExtention + '.xml'
- annotation_path = os.path.join(annotation_dir, annotation_name)
- label_name = nameWithoutExtention + '.txt'
- label_path = os.path.join(yolo_labels_dir, label_name)
- probo = random.randint(1, 100)
- print("Probobility: %d" % probo)
- if(probo < 80): # train dataset
- if os.path.exists(annotation_path):
- train_file.write(image_path + '\n')
- convert_annotation(nameWithoutExtention) # convert label
- copyfile(image_path, yolov5_images_train_dir + voc_path)
- copyfile(label_path, yolov5_labels_train_dir + label_name)
- elif(80 <=probo < 90): # test dataset
- if os.path.exists(annotation_path):
- test_file.write(image_path + '\n')
- convert_annotation(nameWithoutExtention) # convert label
- copyfile(image_path, yolov5_images_test_dir + voc_path)
- copyfile(label_path, yolov5_labels_test_dir + label_name)
- else: # val dataset
- if os.path.exists(annotation_path):
- val_file.write(image_path + '\n')
- convert_annotation(nameWithoutExtention) # convert label
- copyfile(image_path, yolov5_images_val_dir + voc_path)
- copyfile(label_path, yolov5_labels_val_dir + label_name)
- train_file.close()
- test_file.close()
- val_file.close()
然后将整个文档上传到Jetson下的yolo5同级路径下的文件夹内。
![]()
在yolov5-6.1/data/.yaml中先复制一份,改名为ljx.yaml(意义为自己的参数配置)ljx.yaml文件需要修改的参数是nc与names以及你的训练测试路径。nc是标签名个数,names就是标签的名字。
在yolov5-6.1/models先复制一份yolov5s.yaml至ljxs.yaml,更名ljxs.yaml(意为模型),只将如下的nc修改为训练集种类即可
python3 train.py --img 640 --batch 8 --epochs 300 --data ../../yolov5-6.1/data/ljx.yaml --cfg ../../yolov5-6.1/models/ljxs.yaml --weights weights/yolov5s.pt --device '0'
如果出现无法wandb可视化毕业设计记录-yolov5的wandb报错,原因和解决方法(非屏蔽wandb)_芃芃です的博客-CSDN博客

GitHub - ultralytics/yolov5: YOLOv5 🚀 in PyTorch > ONNX > CoreML > TFLite

测试pen
估计使用的数据量太小导致精度太低,小白一个刚开始学习没几天欢迎大佬提点一二