news 2026/10/1 9:23:32

宫颈癌检测数据集YOLOV5格式详解:从目录结构到训练避坑

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
宫颈癌检测数据集YOLOV5格式详解:从目录结构到训练避坑

简介:这是一份面向目标检测与医学影像分析学习者的YOLOV5格式宫颈癌检测数据集,仅包含cancer一个类别,训练集816张图片、验证集216张图片,均为1000-4000分辨率的大尺寸RGB图像,病灶目标小且边界框标注清晰,特别适合研究小目标检测场景。压缩后约614.59MB,共2000个文件,主要由1083个txt标签文件、916个jpeg图像文件和1个可视化py脚本组成;txt标签与图片一一对应,目录已按YOLOV5标准整理,整体按训练集与验证集分目录存放,下载后可直接接入训练,无需额外格式转换。附带的Python可视化脚本无需修改即可运行,随机读取一张图片即可自动绘制边界框并将结果保存到当前目录,便于快速核对标注质量与数据分布。目前已有738人学习下载,适合需要现成医学数据集开展实验或进行小目标检测算法验证的学生与开发者。

1. 宫颈癌检测数据集:YOLOV5目录格式的医学影像数据到底能不能直接用

做医学影像检测的人,大概率都经历过这种尴尬:好不容易找到一份宫颈癌相关的公开数据集,下载下来一看,不是 VOC 就是 COCO,要么就是一堆没标注的原始切片,得自己花两三天转格式、写脚本、划分数据集,等真正能跑起来训练,热情已经消耗了一半。这份医学数据集(YOLOV5目录格式)比较实在——类别就一个,训练集、验证集已经按目录分好,标签文件是 YOLO 标准的 txt,也就是说,你拿到手之后改个 yaml 路径就能直接开训,省掉的是整个数据预处理环节。它解决的核心问题不是"有没有数据",而是"数据能不能立刻喂给 YOLOV5 用",适合正在跑目标检测实验、又不想在数据格式上浪费时间的研究生和算法工程师。这篇文章我会从目录结构、标签格式、训练配置、验证指标到常见的翻车点,把整个流程拆开讲透。

2. 解构 YOLOV5 目录格式:images / labels 与 train / val 的正确摆放方式

2.1 目录树长什么样:为什么 train 和 val 不能混着放

拿到这份数据集,第一件事不是急着配环境,而是把目录结构看明白。YOLOV5 对数据集的目录组织有明确约定:images 和 labels 必须分开放,且 images 下的 train、val 子目录要对应 labels 下的同名子目录。这份数据集按约定来,解压后的结构大致是这样:

cervical_dataset/ ├── images/ │ ├── train/ │ │ ├── 001.jpg │ │ ├── 002.jpg │ │ └── ... │ └── val/ │ ├── 101.jpg │ └── ... ├── labels/ │ ├── train/ │ │ ├── 001.txt │ │ ├── 002.txt │ │ └── ... │ └── val/ │ ├── 101.txt │ └── ... ├── data.yaml └── README.md

这个结构唯一的硬约束是:同名文件必须存在于 images/train 和 labels/train 之下,比如 001.jpg 和 001.txt 要一一对应。训练时 YOLOV5 会通过图片路径去推断标签路径,如果你把一张图放在 train、标签却放在 val,训练脚本直接报错或者静默跳过这张图——后者更坑,数据量少的时候你根本不知道哪张图被丢了。

验证方法很简单,写一段 Python 脚本检查两边的文件名集合是否完全一致:

import os img_train = set(f.split('.')[0] for f in os.listdir('images/train')) lbl_train = set(f.split('.')[0] for f in os.listdir('labels/train')) img_val = set(f.split('.')[0] for f in os.listdir('images/val')) lbl_val = set(f.split('.')[0] for f in os.listdir('labels/val')) print('train 图片数:', len(img_train), '标签数:', len(lbl_train)) print('val 图片数:', len(img_val), '标签数:', len(lbl_val)) print('train 缺失标签:', img_train - lbl_train) print('val 缺失标签:', img_val - lbl_val)

这段脚本的作用是把「图片与标签是否一一对应」做成一次显式检查,输出缺失项。我一般拿到任何 YOLO 格式数据集都会先跑一遍,因为有些二道贩子数据集是从别的格式转过来的,转换脚本写得不干净就会出现漏转或者文件名错位的问题。这也是这份数据集让我放心的地方——目录树是完整的,train 和 val 分离得很干净,不用自己重新划分,省了随机抽样那一步。如果你打算自己扩展数据集,切记保持这个目录树不变,增加图片时同步放好标签,不要单独往 images 里塞文件。

2.2 label 文件的五个数字:类 ID 与归一化坐标的完整解读

YOLO 标签文件和 VOC 最大的不同在于,它不记录像素坐标,而是用归一化后的相对坐标。打开 labels/train 下面的任意一个 txt 文件,你看到的每一行都是五个数字:

0 0.452148 0.318359 0.084961 0.112305

从左到右依次是类别 ID(整数,从 0 开始)、目标中心点的 x 坐标、目标中心点的 y 坐标、目标框的宽度、目标框的高度。后四个值全部是归一化结果,等于实际像素值除以图片宽或高。这份数据集只有一个类别——宫颈癌病变区域,所以类别 ID 恒为 0,这也意味着如果你跑完训练发现类别数对不上,问题大概率出在 data.yaml 而不是标签文件。

有一点值得注意:这份数据集的 txt 文件是纯文本、UTF-8 编码,不存在 BOM 头的问题,YOLOV5 的 dataloader 能直接读。之前我踩过另外一份数据集的坑,标签文件是 GBK 编码带 BOM,训练时没报错但标注框全部是乱的,找了一天才发现是编码问题。所以拿到任何数据集,先用文本编辑器打开一个 label 文件确认编码和格式,比你后面排查一整天值得多。

2.3 数据统计脚本:一次性确认类别、框数量与尺寸分布

在启动训练之前,我习惯先写一个统计脚本,把整个数据集的标注情况摸清楚。别看这一步不起眼,它能直接告诉你这个数据集能不能直接训、需不需要调 anchor 或者做数据增强。脚本思路很直接:遍历所有 txt,统计类别分布、每张图的框数量、框的尺寸分布和宽高比分布。

import os from collections import Counter def parse_label(txt_path): boxes = [] with open(txt_path, 'r') as f: for line in f: parts = line.strip().split() if len(parts) != 5: continue cls, cx, cy, w, h = int(parts[0]), float(parts[1]), float(parts[2]), float(parts[3]), float(parts[4]) boxes.append((cls, cx, cy, w, h)) return boxes all_boxes = [] for split in ['train', 'val']: label_dir = f'labels/{split}' for fn in os.listdir(label_dir): if fn.endswith('.txt'): all_boxes.extend(parse_label(os.path.join(label_dir, fn))) cls_counter = Counter(box[0] for box in all_boxes) img_with_boxes = len(set(os.path.splitext(fn)[0] for fn in os.listdir('labels/train'))) print('类别统计:', dict(cls_counter)) print('总标注框数:', len(all_boxes)) print('小目标占比(<32x32):', sum(1 for box in all_boxes if box[3] * 640 < 32 and box[4] * 640 < 32) / len(all_boxes)) print('中目标占比(32-96):', sum(1 for box in all_boxes if 32 <= box[3] * 640 < 96 and 32 <= box[4] * 640 < 96) / len(all_boxes))

这段脚本默认图片尺寸按 640 计算,因为 YOLOV5 训练时默认会把图片缩放到 640x640。运行后你能看到三个关键数据:类别是否只有 0、小目标占比有多高、中目标占比是多少。宫颈癌病变区域在整张切片里通常占比例很小,属于典型的小目标检测场景。如果小目标占比超过一半,后面训练时就必须考虑 mosaic 增强和 anchor 调整的问题,这两个坑我放到第 5 章展开讲。

3. 训练配置与启动:把宫颈癌检测模型跑起来的关键步骤

3.1 data.yaml 写法:绝对路径还是相对路径

拿到数据集后,训练前唯一必须改的文件是 data.yaml。YOLOV5 官方仓库的 data.yaml 模板长这样,你需要把 path 改成实际目录:

# data.yaml path: /absolute/path/to/cervical_dataset # 数据集根目录,建议用绝对路径 train: images/train val: images/val nc: 1 names: ['cervical_cancer']

这里有几个关键点。path 字段是数据集根目录,train 和 val 是相对于 path 的子路径;nc 必须等于 1,names 列表长度必须也是 1,否则 YOLOV5 在读取时会报类别数不一致。我一般习惯用绝对路径而不是相对路径,因为 YOLOV5 在启动时如果用了不带 path 字段的老版本配置写法(直接写 train: /xxx/images/train),在不同机器上迁移时容易漏改路径。用 path 统一管理之后,整个数据集目录可以整体搬迁而不需要逐个改路径。

还有一个常见问题是 Windows 和 Linux 路径分隔符的差异。如果你在 Windows 上写 path 用了反斜杠,上传到 Linux 服务器后可能解析出错,建议统一用正斜杠或者直接用 yaml 的字符串转义。

3.2 模型选型:YOLOV5s 还是 YOLOV5m

YOLOV5 官方提供了 n/s/m/l/x 五个尺寸的模型。对于这份宫颈癌数据集,我的建议是起步用 YOLOV5s,不要一上来就上 YOLOV5x。原因很简单:单类别检测任务对模型的表达能力要求没那么高,s 模型参数量约 700 万,在 GTX 1080Ti 级别的显卡上 batch size 16 跑 640 分辨率毫无压力,一次实验几分钟能完成,方便快速迭代超参数。如果你把模型换成 x,同样一轮训练时间翻几倍,学术实验可以接受,但工程上验证思路的效率太低了。

选型时真正值得关注的是输入分辨率 img-size 和 anchor。YOLOV5 默认的输入尺寸是 640,但这份数据集的原始图片如果尺寸不统一——比如有的是 1024 有的是 768——YOLOV5 会在 dataloader 里自动做 letterbox 缩放,把长边统一到目标尺寸。这里有个隐藏问题:如果你的图片原始尺寸远大于 640,比如是 2000 像素级别的病理切片,直接在 640 下训练会把病变区域缩得很小,检测效果断崖式下降。这种情况我建议把 img-size 提到 1024 或 1280,代价是显存占用变大,但小目标检测收益明显。第 6 章我会专门讲这个。

3.3 train.py 关键参数:epochs、batch、workers 的工程取值

启动训练的命令并不复杂,关键在参数怎么设置。以下是我在这份数据集上常用的启动命令:

python train.py \ --data data.yaml \ --weights yolov5s.pt \ --img 640 \ --batch 16 \ --epochs 100 \ --workers 4 \ --seed 42 \ --name cervical_yolov5s

逐项说明:--data 指定数据配置文件;--weights 是预训练权重,YOLOV5 官方提供在 COCO 上预训练好的 yolov5s.pt,直接用它做迁移学习比从零训收敛快得多;--img 是输入分辨率;--batch 按显卡显存调整,16 对应 8GB 以上显存,如果显卡只有 6GB 建议降到 8;--workers 是数据加载进程数,Windows 上设置过大会报错,Linux 上 4 到 8 都可以;--seed 固定随机种子,保证实验可复现;--name 是实验名,保存到 runs/train/ 下,避免每次覆盖之前的实验结果。

epochs 的取值没有绝对标准。100 epoch 对单类别小型数据集通常是够的,但我建议你开训练后盯住验证集的 loss 曲线——如果到 60 个 epoch 之后 val loss 不再下降甚至上升,那就是过拟合了,提前停掉就行,不用死等 100 轮。数据量很小时不要用太高的 epochs,否则模型会把训练集的噪声也背下来,推理时在真实切片上表现很差。

4. 验证与结果判读:别只看 mAP,还要看 PR 曲线和误检来源

4.1 val.py 验证命令与输出文件说明

训练结束后,用 val.py 在验证集上评估是标准流程。命令如下:

python val.py \ --data data.yaml \ --weights runs/train/cervical_yolov5s/weights/best.pt \ --img 640 \ --batch 16 \ --name cervical_val

验证完成后,YOLOV5 会在 runs/val/cervical_val 下生成一堆文件,包括 labels.jpg、混淆矩阵 confusionMatrix.png、PR 曲线 PR_curve.png、F1 曲线等。这些图才是真正值得花时间看的东西,而不是只看终端输出的那个 mAP 数字。

4.2 医学场景下 precision 和 recall 哪个优先

这是一个很容易被忽略但极其重要的点。普通物体检测比赛,大家拼的是 mAP,但医学检测场景下 recall(召回率)和 precision(精确率)的优先级排序完全不同。宫颈癌筛查这类场景,漏检一个病变区域是严重的医疗事故隐患,所以 recall 的优先级要高于 precision——宁可多框一些疑似区域让医生复审,也不能漏掉真实的病灶。

YOLOV5 的 checkpoint 保存逻辑是按验证集综合指标选 best.pt 和 last.pt,如果你想要一个更偏 recall 的模型,可以在 val.py 的参数里调整 conf-thres 和 iou-thres。比如把 conf-thres 从默认的 0.25 降到 0.1,会检出更多低置信度的目标,recall 上升但 precision 下降,这是用阈值换召回的做法,医学预处理场景常用。具体操作是:

python val.py --data data.yaml --weights best.pt --conf-thres 0.1 --iou-thres 0.5

跑完对比一下 PR 曲线,你能直观看到阈值变化带来的 trade-off。我一般会在项目里同时保留两个版本——一个高 precision 用于自动筛查,一个高 recall 用于辅助医生复核。

4.3 可视化推理:predict.py 看实际框出效果

验证集的指标再好看,最终要过可视化这一关。拿几张验证集图片跑一下推理,直接看模型框出来的区域和真实标注框的差异:

python detect.py \ --weights runs/train/cervical_yolov5s/weights/best.pt \ --source ../cervical_dataset/images/val \ --img 640 \ --conf 0.25 \ --save-txt \ --save-conf

用 --save-txt 可以把检测结果保存成 txt 格式,--save-conf 会在 txt 里写入置信度。这一步的意义在于:你肉眼看到的 false positive 和 false negative 是判断模型能否实际部署的最直接证据。比如你发现模型经常把宫颈腺体误判成病变区域,那就说明训练数据里可能缺少这类阴性样本,后续数据采集方向就很明确了。

5. 避坑记录:标注框、类别不平衡与小目标的四个典型翻车现场

5.1 标注框坐标越界或归一化错误:训练不报错但 mAP 异常低

现象:训练过程完全正常,loss 正常下降,但验证集 mAP 一直在 0.3 以下徘徊,怎么看都不对劲。

原因:标签文件里某个框的 x_center + w/2 大于 1,或者 y_center - h/2 小于 0,导致目标框一部分超出图片边界。YOLOV5 本身不会报错,但计算 IoU 的时候这些越界框会严重干扰 loss 和 mAP。这种问题常见于由 VOC 转 YOLO 时坐标换算出错,或者标注工具导出时精度损失。

解决:跑统计脚本把所有标签中的坐标值打印出来,检查每个值是否都在 [0, 1] 区间内。发现越界的,要么修标注工具,要么用脚本过滤掉这些框。我从那以后每次拿到数据集,都会先跑一遍坐标范围检查,这是最低成本的防翻车动作。

5.2 单类别数据集 loss 震荡:为什么只检测一个类别还会过拟合

现象:验证集 loss 前期下降正常,到 50 epoch 之后开始上下震荡,训练集 loss 却还在下降,典型的过拟合信号。

原因:这份数据集总量不大,且单类别目标形态单一,模型很容易把训练集的背景纹理也学进去。很多人以为单类别任务简单,其实恰恰相反,单类别模型缺少类别间的区分约束,更容易记住背景细节。加上训练时如果开了过强的 mosaic 增强,会不断产生新背景,让模型在真实验证集上反而表现不稳定。

解决:把 epochs 控制在 80 以内,早停回调设 patience=15,同时降低 augment 强度——具体是把 hsv_h、hsv_s、degrees 这几个参数的值调小,不要用默认的强增强策略。我一般会在训练命令里追加:

--hyp hyp.scratch-low.yaml

这个低增强配置对医学影像尤其合适,因为医学图像的拍摄条件相对固定,不需要模拟太多自然场景的光照变化。

5.3 小目标漏检严重:anchor 尺寸不匹配是最隐蔽的原因

现象:肉眼能看到的小病变区域,模型在可视化结果里就是框不出来,mAP 对小目标尤其低。

原因:YOLOV5 默认的 anchor 是基于 COCO 数据集统计出来的,COCO 里小目标占比不小但目标类别多尺寸分散。而宫颈癌病变区域通常在整个图片中只占 5% 以下,尺度分布和 COCO 差异很大。直接用默认 anchor 训练,小目标匹配不到合适的 anchor,自然检不出来。

解决:在训练前用 YOLOV5 仓库自带的 anchor 聚类脚本,对这份数据集的标注框重新聚类:

python utils/autoanchor.py --cfg models/yolov5s.yaml --data data.yaml --img 640

脚本会把新的 anchor 写进模型配置文件。你会发现聚类出来的 anchor 尺寸明显比默认值小,这就是数据集的真实尺度分布。重新聚类后再训练,小目标 recall 通常有可感知的提升。

5.4 重叠目标与 NMS 参数:为什么同一区域被框了三次

现象:一张图上同一个病变区域被输出 3 个重叠框,置信度都挺高,但真实标注只有一个框。

原因:医学图像中病变区域往往边界模糊、高密度接近,模型在相邻特征位置产生多个高响应,NMS 的 IoU 阈值过严或过松都会出问题。YOLOV5 默认 NMS IoU 阈值是 0.45,但在密集目标场景下,真实的同一个目标的两个预测框 IoU 可能超过 0.5,被 NMS 保留下来。

解决:调高 NMS 的 IoU 阈值到 0.6 或 0.65,让更重叠的框被抑制掉。如果你在 detect.py 阶段发现重复框,直接加 --iou-thres 0.6 即可。另外注意 YOLOV5 的训练阶段和推理阶段 NMS 策略是分开的,训练时不要动 NMS 参数,只对最终的 detect 和 val 生效。

6. 进阶:医学图像数据增强的度在哪里,用小目标增强提升宫颈癌检测的召回率

数据增强是目标检测绕不开的环节,但医学影像的数据增强策略和自然图像完全不同。自然图像可以放心用旋转、翻转、色彩抖动,因为物体的语义不受影响,但医学图像里方向是有意义的——病理切片虽然旋转不影响诊断,但宫颈镜图像的拍摄角度和光照条件相对固定,过强的增强反而会让模型学到虚假的形态变化。

我在这份数据集上验证过一组比较实用的增强配置。YOLOV5 的 mosaic 增强建议开启但概率保持在 0.5 左右,它能把多张图拼接成一张,对小目标检测有利,但不要全程开启,训练后期关掉能让模型适应真实背景。翻转增强只保留水平翻转,垂直翻转对于宫颈图像会引入方向歧义。色彩增强降级到默认值的一半。

如果你想进一步提小目标 recall,我试过最有效的手段是 cutout 和 copy-paste 的组合,把局部病变区域复制粘贴到背景区域来扩充小目标样本。常见做法是先用统计脚本找出所有小目标框,再随机复制到同尺寸的空白区域,注意不要覆盖已有标注框。YOLOV5 官方没有直接支持 copy-paste,但可以在数据加载前用脚本离线增强一次,本质上是对小目标进行过采样。实测下来,小目标 recall 能提升 3 到 5 个点,代价是训练时间多 10% 左右。

那次我做宫颈癌检测项目时,试了很多增强组合,最后发现其实验证集 mAP 提升不大,反而是把小目标增强放在离线阶段做、在线训练保持低增强,最终部署时误检率最低。从那以后,我每次处理医学数据集都强制走一遍统计脚本、坐标检查、anchor 聚类这三步,再开始调增强参数——顺序乱一时,返工两小时。希望这份材料的流程也能帮你在数据准备阶段少走弯路,把更多时间留给真正值得调的东西。

本文还有配套的精品资源,点击获取

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/10/1 9:23:03

银河麒麟V10 SP1重装保留数据盘:手动分区与fstab挂载避坑

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华
网站建设 2026/10/1 9:22:25

C#集成YOLOv8与TensorRT+ByteTrack:跨语言目标追踪落地实践

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华
网站建设 2026/10/1 9:21:47

Linux键盘输入全解析:从termios到evdev的完整链路

先把话说在前头&#xff1a;Linux下“读取键盘输入”这件事&#xff0c;看起来就是调一个scanf或者getchar的事&#xff0c;但一旦你开始较真——比如要读方向键、要监听按键时长、要在终端里做“按下立即响应”的交互&#xff0c;或者干脆想写一个按键记录工具&#xff0c;你就…

作者头像 李华
网站建设 2026/10/1 9:20:56

服务器安全实战:攻击面盘点、日志审计与入侵排查

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华
网站建设 2026/10/1 9:19:56

Jev 模型接入 TraeCode 与 Windows 本地部署实战指南

1. 从热搜词里读懂 Jev 到底是什么1.1 一个被搜索词“拼”出来的技术画像先把热搜词摊开看一遍&#xff1a;jev、jev模型官网、jev模型是什么、jev模型开源吗、jev模型申请、jev密钥、jev本地部署、jev windows 部署、jev使用、jev ai、jev聊天助手 github、jev在codex中使用、…

作者头像 李华
网站建设 2026/10/1 9:19:50

ESP32智能家居实战:基于WiFi+BLE的一站式搭建方案

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华