当前位置: 首页 > news >正文

深度学习------YOLOv5《第二篇》

目录

一、马赛克增强:为什么需要 “拼接”?

二、图像拼接:4 张图如何 “拼” 成一张?

1. 确定拼接中心与边界

2. 计算每张图的放置区域

3. 图像填充与偏移量计算

三、标签映射:目标框如何从 “小图” 到 “大图”?

四、边界修正与增强:让拼接更 “合理”

五、框架关联:PyTorch 与 TensorFlow 的实现差异

六、总结


YOLOv5 马赛克数据增强底层解析:从图像拼接到底层坐标映射

    在目标检测模型的训练中,数据增强是提升模型鲁棒性的关键手段。YOLOv5 作为主流的目标检测框架,其datasets.py中实现的马赛克(Mosaic)数据增强技术尤为经典 —— 通过将 4 张图片拼接成一张大图,能让模型同时学习不同场景、不同尺度的目标特征。本文将聚焦datasets.py中 655-697 行的核心代码,解析马赛克增强的图像拼接逻辑、坐标映射细节,以及与深度学习框架的关联。

一、马赛克增强:为什么需要 “拼接”?

      传统的数据增强(如旋转、裁剪)多基于单张图片,而马赛克增强创新性地将 4 张图片拼接为一张训练样本,其优势在于:

  • 增加目标密度:让模型在单张图中学习更多目标的共存关系;
  • 丰富场景多样性:融合不同背景、光照、尺度的图像,提升模型泛化能力;
  • 降低小目标漏检率:拼接后小目标占比相对提升,强化模型对小目标的感知。

      YOLOv5 的load_mosaic函数正是实现这一逻辑的核心,我们重点解析其图像拼接与标签调整的底层代码。

二、图像拼接:4 张图如何 “拼” 成一张?

      在load_mosaic函数中,655 行左右的代码负责将 4 张图片按 “左上 - 右上 - 左下 - 右下” 的布局拼接到一张 2 倍于目标尺寸的大图中(默认目标尺寸为 640x640,故大图为 1280x1280)。核心逻辑可拆解为 3 步:

1. 确定拼接中心与边界

s = self.img_size  # 目标尺寸,如640
yc, xc = [int(random.uniform(-x, 2 * s + x)) for x in self.mosaic_border]  # 马赛克中心坐标(xc, yc)
indices = [index] + [random.randint(0, len(self.labels) - 1) for _ in range(3)]  # 4张图片的索引
  • mosaic_border为边界补偿(默认[-320, -320]),让中心坐标(xc, yc)可在(-320, 1560)范围内随机生成,增加拼接随机性;
  • indices选取 1 张当前图 + 3 张随机图,共 4 张参与拼接。

2. 计算每张图的放置区域

以 4 张图的放置位置为例(代码 655-670 行):

# 第1张图(左上)
x1a, y1a, x2a, y2a = max(xc - w, 0), max(yc - h, 0), xc, yc  # 大图中放置区域(左上-右下)
x1b, y1b, x2b, y2b = w - (x2a - x1a), h - (y2a - y1a), w, h  # 小图中被截取的区域(左上-右下)# 第2张图(右上)
x1a, y1a, x2a, y2a = xc, max(yc - h, 0), min(xc + w, s * 2), yc
x1b, y1b, x2b, y2b = 0, h - (y2a - y1a), min(w, x2a - x1a), h# 第3张图(左下)、第4张图(右下)逻辑类似...
  • 变量说明:w, h为当前小图的宽高;x1a, y1a为小图在大图中的左上角坐标,x2a, y2a为右下角坐标;
  • 核心逻辑:通过中心坐标(xc, yc)计算每张小图在大图中的放置范围,同时确定小图中需要被截取的区域(避免超出大图边界)。

3. 图像填充与偏移量计算

# 将小图的截取区域填充到大图
img4[y1a:y2a, x1a:x2a] = img[y1b:y2b, x1b:x2b]# 计算偏移量(关键!用于后续标签坐标转换)
padw = x1a - x1b  # 水平方向偏移(大图放置位置 - 小图截取位置)
padh = y1a - y1b  # 垂直方向偏移
  • mg4是初始化的 1280x1280 大图(填充灰色[114, 114, 114]),通过切片操作将小图的有效区域填充进去;
  • padwpadh横纵方向的填充偏移量,这两个值是后续标签坐标从 “小图” 映射到 “大图” 的核心参数。

三、标签映射:目标框如何从 “小图” 到 “大图”?

      拼接图像后,需要同步调整目标框坐标(代码 676-682 行),确保标签与拼接后的目标位置对应。假设小图中目标的归一化坐标为(x, y, w, h)(中心 x、中心 y、宽、高),转换逻辑如下:

# 小图中目标框的归一化坐标 -> 像素坐标(x1, y1, x2, y2)
labels[:, 1] = w * (x[:, 1] - x[:, 3] / 2) + padw  # 左上角x
labels[:, 2] = h * (x[:, 2] - x[:, 4] / 2) + padh  # 左上角y
labels[:, 3] = w * (x[:, 1] + x[:, 3] / 2) + padw  # 右下角x
labels[:, 4] = h * (x[:, 2] + x[:, 4] / 2) + padh  # 右下角y
  • 步骤 1:将归一化坐标转换为小图的像素坐标(乘以小图宽高w, h);
  • 步骤 2:加上偏移量padw, padh,得到目标框在大图中的像素坐标。

四、边界修正与增强:让拼接更 “合理”

拼接后的大图可能存在目标框超出边界的问题,需通过代码 690-697 行修正:

# 合并4张图的标签并裁剪超出大图范围的坐标
if len(labels4):labels4 = np.concatenate(labels4, 0)np.clip(labels4[:, 1:], 0, 2 * s, out=labels4[:, 1:])  # 裁剪到0~1280范围

随后,拼接好的大图会进一步通过random_perspective函数进行旋转、平移、尺度缩放等增强(代码 682-688 行),模拟更复杂的拍摄角度:

img4, labels4 = random_perspective(img4, labels4,degrees=self.hyp['degrees'],  # 旋转角度translate=self.hyp['translate'],  # 平移比例scale=self.hyp['scale'],  # 缩放比例shear=self.hyp['shear'],  # 剪切角度perspective=self.hyp['perspective'])  # 透视变换

这些操作让马赛克样本更接近真实场景,进一步提升模型的鲁棒性。

五、框架关联:PyTorch 与 TensorFlow 的实现差异

这段代码基于 PyTorch 实现,其设计与 PyTorch 的数据加载逻辑深度绑定:

  • 继承Dataset类:LoadImagesAndLabels作为自定义数据集,通过__getitem__方法返回增强后的图像与标签,适配 PyTorch 的DataLoader
  • 延迟加载与缓存:通过load_image函数按需加载图像,支持缓存机制(cache_images),平衡内存占用与加载速度;
  • 张量转换:最终通过torch.from_numpy将图像和标签转换为 PyTorch 张量,直接用于模型训练。

而 TensorFlow 中类似的逻辑通常基于tf.data.Dataset实现,通过map函数串联增强操作,两者核心思想一致(数据管道 + 惰性计算),但 API 风格不同:

  • PyTorch 更灵活,支持 Python 原生逻辑(如本文中的 numpy 操作);
  • TensorFlow 更偏向于图计算,适合大规模分布式训练。

六、总结

      YOLOv5 的马赛克增强通过 “4 图拼接 - 坐标映射 - 边界修正 - 二次增强” 的流程,高效提升了训练样本的多样性。其中padwpadh的偏移量计算是标签映射的核心,而 PyTorch 的灵活数据加载机制则为这一复杂增强提供了高效支持。理解这部分代码,不仅能帮助我们调优数据增强策略,更能深入掌握目标检测中 “数据驱动” 的核心逻辑。# YOLOv5 马赛克数据增强底层解析:从图像拼接到底层坐标映射

      在目标检测模型的训练中,数据增强是提升模型鲁棒性的关键手段。YOLOv5 作为主流的目标检测框架,其datasets.py中实现的马赛克(Mosaic)数据增强技术尤为经典 —— 通过将 4 张图片拼接成一张大图,能让模型同时学习不同场景、不同尺度的目标特征。本文将聚焦datasets.py中 655-697 行的核心代码,解析马赛克增强的图像拼接逻辑、坐标映射细节,以及与深度学习框架的关联。

http://www.dtcms.com/a/524706.html

相关文章:

  • Google Drive 超大文件下载到服务器
  • vscode中Java开发环境的配置
  • 【穿越Effective C++】条款5:了解C++默默编写并调用哪些函数——编译器自动生成的秘密
  • docker镜像从服务器Acopy到服务器B
  • 网站开发微信端小说网站如何建设
  • 网站建设黄页视频wordpress的标签设置主页
  • 学习java线程池ThreadPoolExecutor类使用介绍
  • 有关建设旅行网站的建设负责网站的建设规划
  • 学Java第三十七天-------常用API
  • 微信漫画网站模板wordpress 视频展示
  • 【NestJS】依赖注入:超越自动new的深层解析
  • 北京网站建设策划建设公司长春建站培训
  • Mac常用软件
  • 【Linux笔记】网络部分——基于Socket套接字实现最简单的HTTP协议服务器
  • Linux基础知识(三、Linux常见操作目录命令)
  • 类似凡科建站的平台手机网站仿站
  • 在网站文字上做笔记设计制作中国第一架飞机的人是
  • C++ 分治 快速选择算法 堆排序 TopK问题 力扣 215. 数组中的第K个最大元素 题解 每日一题
  • 永磁同步电机无速度算法--基于相位超前校正的LESO
  • 动态 静态 网站地图合肥庐阳区建设局网站
  • JavaEE开篇之计算机是如何工作的
  • 基于python机器学习的农产品价格数据分析与预测的可视化系统
  • 如何通过掌纹识别实现Windows工作站安全登录:从技术原理到企业级落地实践
  • 正则表达式全集
  • 中山手机网站制作哪家好网站管理员登陆后缀
  • K8s高可用:四大核心机制解析
  • 1024勋章发文活动
  • 依托金仓数据库的医疗信创多院区实践与 KingbaseES 操作详解
  • Linux---开发工具2
  • GBase安装部署