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

copy_paste

1、copy_paste

  如果一张图像中有 segmentation 标注,则可以将标注的物体 copy 出来,paste 到你指定的地方。若没有 segmentation 标注,则无法使用 copy_paste 增强方式

1)将一张图像中的物体 copy 出来,paste 在本图像中 (yolov5 中的做法)

2)更常用的是 :将 一张图像中的物体 copy 出来,paste 到另外一张图像中


2、代码示例

例 1、将一张图像中的物体 copy 出来,paste 在本图像中

代码说明

  • 按照指定比例 copy-paste 图像中的部分 object, 比如,一张图像中有 10个 object,设置的 copy-paste 概率为 0.5,那么将有 大概5个物体会被 copy-paste

  • 将图片镜像 并从中 copy 出 (镜像的) object,如果 (镜像的) object 的 bbox 与 原图像中的任意一个 bbox 交集面积 都不大于 0.3,则将 (镜像的) object paste 到另外一张图像中

  • bbox 和 segmentation 标注也要进行合并

import numpy as np
import random
import torch
from pycocotools.coco import COCO
import math
import cv2dataDir = '/Users/dataset/COCO2017'
annFile = '{}/annotations/instances_val2017.json'.format(dataDir)
imgFile = '{}/val2017'.format(dataDir)img_size = 640def bbox_ioa(box1, box2, eps=1e-7):"""Returns the intersection over box2 area given box1, box2.Boxes are x1y1x2y2box1:       np.array of shape(4)box2:       np.array of shape(nx4)returns:    np.array of shape(n)"""# Get the coordinates of bounding boxesb1_x1, b1_y1, b1_x2, b1_y2 = box1b2_x1, b2_y1, b2_x2, b2_y2 = box2.T# Intersection areainter_area = (np.minimum(b1_x2, b2_x2) - np.maximum(b1_x1, b2_x1)).clip(0) * (np.minimum(b1_y2, b2_y2) - np.maximum(b1_y1, b2_y1)).clip(0)# box2 areabox2_area = (b2_x2 - b2_x1) * (b2_y2 - b2_y1) + eps# Intersection over box2 areareturn inter_area / box2_areadef copy_paste(im, labels, segments, p=0.5):"""Applies Copy-Paste augmentation by flipping and merging segments and labels on an image.Details at https://arxiv.org/abs/2012.07177."""n = len(segments)if p and n:h, w, c = im.shape  # height, width, channelsim_new = np.zeros(im.shape, np.uint8)for j in random.sample(range(n), k=round(p * n)):l, s = labels[j], segments[j]box = w - l[3], l[2], w - l[1], l[4]ioa = bbox_ioa(box, labels[:, 1:5])  # intersection over areaif (ioa < 0.30).all():  # allow 30% obscuration of existing labelslabels = np.concatenate((labels, [[l[0], *box]]), 0)segments.append(np.concatenate((w - s[:, 0:1], s[:, 1:2]), 1))cv2.drawContours(im_new, [segments[j].astype(np.int32)], -1, (1, 1, 1), cv2.FILLED)result = cv2.flip(im, 1)  # augment segments (flip left-right)i = cv2.flip(im_new, 1).astype(bool)im[i] = result[i]return im, labels, segmentsif __name__ == '__main__':coco = COCO(annFile)indices = range(len(coco.imgs))file_names = []labels = []segments = []for i in coco.imgs:file_names.append(coco.imgs[i]['file_name'])img_w, img_h = coco.imgs[i]['width'], coco.imgs[i]['height']labels_one_img = []segments_one_img = []for ann in coco.imgToAnns[i]:if ann['iscrowd'] == 0:category_id = ann['category_id']bbox_xywh = ann['bbox']bbox_xyxy = bbox_xywh[0], bbox_xywh[1], bbox_xywh[0]+bbox_xywh[2], bbox_xywh[1]+bbox_xywh[3]labels_one_img.append(np.array([category_id, *bbox_xyxy]))segmentation = np.array(ann['segmentation'][0]).reshape((-1, 2))segments_one_img.append(segmentation)labels.append(np.array(labels_one_img))segments.append(segments_one_img)# 随便指定一张图像index = 46img_original = cv2.imread(imgFile + '/' + file_names[index])one_img_labels = labels[index]one_img_segments = segments[index]img, one_img_labels, one_img_segments = copy_paste(img_original, one_img_labels, one_img_segments, p=0.5)# # 可视化 segmentation# for seg in one_img_segments:#     points = np.array(seg).reshape((-1, 2)).astype(np.int32)#     cv2.drawContours(img, [points], -1, (0, 0, 255), thickness=2)# # 可视化 bbox# for rect in one_img_labels:#     cv2.rectangle(img, (int(rect[1]), int(rect[2])), (int(rect[3]), int(rect[4])), color=(0, 0, 255), thickness=2)cv2.imshow('img', img)cv2.waitKey()cv2.destroyAllWindows()


例 2、将 一张图像中的物体 copy 出来,paste 到另外一张图像中

  • 按照指定比例 copy 图像1 中的部分 object,paste 到图像2中, 比如,图像1 中有 10个 object,设置的 copy-paste 概率为 0.5,那么将有 大概5个物体会被 paste 到图像2中

  • 如果图像1中的物体的 bbox 与 图像2 中的任意一个 bbox 交集面积 都不大于 0.3,则将图片1 中的物体 copy-paste 到图像2中

  • bbox 和 segmentation 标注也要进行合并

import numpy as np
import random
import torch
from pycocotools.coco import COCO
import math
import cv2dataDir = '/Users/dataset/COCO2017'
annFile = '{}/annotations/instances_val2017.json'.format(dataDir)
imgFile = '{}/val2017'.format(dataDir)img_size = 640def bbox_ioa(box1, box2, eps=1e-7):"""Returns the intersection over box2 area given box1, box2.Boxes are x1y1x2y2box1:       np.array of shape(4)box2:       np.array of shape(nx4)returns:    np.array of shape(n)"""# Get the coordinates of bounding boxesb1_x1, b1_y1, b1_x2, b1_y2 = box1b2_x1, b2_y1, b2_x2, b2_y2 = box2.T# Intersection areainter_area = (np.minimum(b1_x2, b2_x2) - np.maximum(b1_x1, b2_x1)).clip(0) * (np.minimum(b1_y2, b2_y2) - np.maximum(b1_y1, b2_y1)).clip(0)# box2 areabox2_area = (b2_x2 - b2_x1) * (b2_y2 - b2_y1) + eps# Intersection over box2 areareturn inter_area / box2_areadef copy_paste(img_1, img1_labels, img1_segments, img_2, img2_labels, img2_segments, p=0.5):"""Applies Copy-Paste augmentation by flipping and merging segments and labels on an image.Details at https://arxiv.org/abs/2012.07177.将 img_1 中的 object copy-paste 到 img_2 中"""n = len(img1_segments)if p and n:img_1_h, img_1_w, _ = img_1.shapeimg_2_h, img_2_w, _ = img_2.shapemin_h, min_w = min(img_1_h, img_2_h), min(img_1_w, img_2_w)img_mask = np.zeros((min_h, min_w, 3), np.uint8)for j in random.sample(range(n), k=round(p * n)):l, s = img1_labels[j], img1_segments[j]ioa = bbox_ioa(l[1:5], img2_labels[:, 1:5])  # intersection over areaif (ioa < 0.30).all():  # allow 30% obscuration of existing labels# 边界情况要再处理一下img2_labels = np.concatenate((img2_labels, [l]), 0)img2_segments.append(s)cv2.drawContours(img_mask, [img1_segments[j].astype(np.int32)], -1, (1, 1, 1), cv2.FILLED)img_mask = img_mask.astype(bool)img_2[:min_h, :min_w, :][img_mask] = img_1[:min_h, :min_w, :][img_mask]return img_2, img2_labels, img2_segmentsif __name__ == '__main__':coco = COCO(annFile)indices = range(len(coco.imgs))file_names = []labels = []segments = []for i in coco.imgs:file_names.append(coco.imgs[i]['file_name'])img_w, img_h = coco.imgs[i]['width'], coco.imgs[i]['height']labels_one_img = []segments_one_img = []for ann in coco.imgToAnns[i]:if ann['iscrowd'] == 0:category_id = ann['category_id']bbox_xywh = ann['bbox']bbox_xyxy = bbox_xywh[0], bbox_xywh[1], bbox_xywh[0]+bbox_xywh[2], bbox_xywh[1]+bbox_xywh[3]labels_one_img.append(np.array([category_id, *bbox_xyxy]))segmentation = np.array(ann['segmentation'][0]).reshape((-1, 2))segments_one_img.append(segmentation)labels.append(np.array(labels_one_img))segments.append(segments_one_img)# 随便指定2张图像index = [46, 2]img_1 = cv2.imread(imgFile + '/' + file_names[index[0]])img_2 = cv2.imread(imgFile + '/' + file_names[index[1]])# 第 1 张图像中的 labels 和 segmentationsimg1_labels = labels[index[0]]img1_segments = segments[index[0]]# 第 2 张图像中的 labels 和 segmentationsimg2_labels = labels[index[1]]img2_segments = segments[index[1]]img_2, img2_labels, img2_segments = copy_paste(img_1, img1_labels, img1_segments, img_2, img2_labels, img2_segments, p=1)# 可视化 segmentationfor seg in img2_segments:points = np.array(seg).reshape((-1, 2)).astype(np.int32)cv2.drawContours(img_2, [points], -1, (0, 0, 255), thickness=2)# # 可视化 bbox# for rect in img2_labels:#     cv2.rectangle(img_2, (int(rect[1]), int(rect[2])), (int(rect[3]), int(rect[4])), color=(0, 0, 255), thickness=2)cv2.imshow('copy-paste img', img_2)cv2.waitKey()cv2.destroyAllWindows()

 

相关文章:

  • 力扣-98.验证二叉搜索树
  • OA 系统办公自动化包含哪些内容,关键功能模块与操作要点说明
  • CodeBuddy 接入 MCP,一键生成网站!
  • 操作系统期末复习笔记
  • HCIP-Datacom Core Technology V1.0_1认识网络设备
  • 计算机网络:移动通信蜂窝网络指的是什么?
  • AI编程:使用Trae + Claude生成原型图,提示词分享
  • 集星云推碰一碰源码搭建的核心模块
  • 2005-2022年各省绿色信贷水平测算数据(含原始数据+计算过程+计算结果)
  • 【CSS】使用 CSS 绘制三角形
  • 【Alist+RaiDrive挂载网盘到本地磁盘】
  • 673SJBH基于ASP的公交系统
  • 电脑内存智能监控清理,优化性能的实用软件
  • UPS是什么?UPS 不间断电源有哪些适配的升压芯片?
  • ET ProcessInnerSender类(实体) 分析
  • 场景以及八股复习篇
  • 图像采集卡的核心功能功与应用详解
  • MQ防重复消费----去重表结合 Spring AOP 切面编程,抽象封装成通用幂等注解
  • Maplibgre-gl 学习1 初识
  • Maven构建流程详解:如何正确管理微服务间的依赖关系-当依赖的模块更新后,我应该如何重新构建主项目
  • 现场丨在胡适施蛰存等手札与文献间,再看百年光华
  • 博柏利上财年营收下降17%,计划裁员1700人助推股价涨超18%
  • 七旬男子驾“老头乐”酒驾被查,曾有两次酒驾两次肇事记录
  • 刘永明|在从普及到提高中发展新大众文艺
  • 2025上海科技节本周六启幕,机器人和科学家同走AI科学红毯
  • “饿了么”枣庄一站点两名连襟骑手先后猝死,软件显示生前3天每日工作超11小时