深度学习图片数据标签切割转换,相对坐标
我们图片分类的标签可能有多个类,一张图片中有大目标和小目标,我们要切割出大目标,然后小目标的坐标也变成相对于大目标的坐标。因为我们为了方便,一次性打标了,一次性的标注了图片中的大目标和小目标,所以小目标的标注坐标是相对于整张图片的,但现在我们要做两次检测,所以切出来的大目标中含有的小目标我们需要做个坐标转换,把小目标的坐标转换成相对于大目标的。
代码如下:
import glob, math, os
import numpy as np
import cv2
from PIL import Image
if __name__ == '__main__':
yolo_dataset_path = 'D://baozi/baozilabel/' #要切割的图片的数据路径
roi_save_path = 'D://baozi//roi1//' #保存切割后的图片数据的路径
# 把所有的txt数据都转化成需要的数据
img_label_infos = dict()
img_path_list = glob.glob(yolo_dataset_path + "//*.jpg")
print(len(img_path_list))
print(img_path_list[0])
for img_path_item in img_path_list:
label_one_infos = []
label_two_infos = []
txt_path = img_path_item[:-3] + 'txt'
# 判断是否存在这个txt
if os.path.exists(txt_path):
img = cv2.imread(img_path_item)
width = img.shape[1]
heigth = img.shape[0]
with open(txt_path) as f:
lines_infos = f.readlines()
for line_item in lines_infos:
line_item_split = line_item.split()
if line_item_split[0] == '1':
line_item_split_float = np.array(line_item_split).astype(np.float)
small_width = int(line_item_split_float[3] * width)
small_height = int(line_item_split_float[4] * heigth)
top_x = int(line_item_split_float[1] * width - small_width / 2)
top_y = int(line_item_split_float[2] * heigth - small_height / 2)
bottom_x = int(line_item_split_float[1] * width + small_width / 2)
bottom_y = int(line_item_split_float[2] * heigth + small_height / 2)
center_x = int(line_item_split_float[1] * width)
center_y = int(line_item_split_float[2] * heigth)
label_one_infos.append([top_x, top_y, small_width, small_height, bottom_x, bottom_y,center_x,center_y])
# 这里进行保存roi图片,命名规则:图片名_top_x_top_y_small_width_small_height
roi_img = img[top_y:(top_y + small_height), top_x:(top_x + small_width)]
save_name = os.path.join(roi_save_path,
os.path.basename(img_path_item)[:-4] + "_{}_{}_{}_{}.jpg".format(top_x,
top_y,
small_width,
small_height))
cv2.imwrite(save_name, roi_img)
pass
elif line_item_split[0] == '0':
line_item_split_float = np.array(line_item_split).astype(np.float)
small_width = int(line_item_split_float[3] * width)
small_height = int(line_item_split_float[4] * heigth)
top_x = int(line_item_split_float[1] * width - small_width / 2)
top_y = int(line_item_split_float[2] * heigth - small_height / 2)
bottom_x = int(line_item_split_float[1] * width + small_width / 2)
bottom_y = int(line_item_split_float[2] * heigth + small_height / 2)
center_x = int(line_item_split_float[1] * width)
center_y = int(line_item_split_float[2] * heigth)
label_two_infos.append(
[top_x, top_y, small_width, small_height, bottom_x, bottom_y, center_x, center_y])
img_label_infos[img_path_item] = [label_one_infos.copy(), label_two_infos.copy()]
for img_path, label_infos in img_label_infos.items():
for plate_label_info_item in label_infos[0]:
label_txt_path = os.path.join(roi_save_path, os.path.basename(img_path)[:-4] + "_{}_{}_{}_{}.txt".format(
plate_label_info_item[0], plate_label_info_item[1], plate_label_info_item[2],
plate_label_info_item[3], ))
with open(label_txt_path, 'w') as f:
for small_label_info_item in label_infos[1]:
# 判读是否在碗碟里面
if small_label_info_item[6]>plate_label_info_item[0]and small_label_info_item[6]<plate_label_info_item[4] and small_label_info_item[7]>plate_label_info_item[1]and small_label_info_item[7]<plate_label_info_item[5]:
center_x=float((small_label_info_item[0]-plate_label_info_item[0])+small_label_info_item[2]/2)/plate_label_info_item[2]
center_y=float((small_label_info_item[1]-plate_label_info_item[1]+small_label_info_item[3]/2))/plate_label_info_item[3]
small_width_scale=float(small_label_info_item[2])/plate_label_info_item[2]
small_height_scale=float(small_label_info_item[3])/plate_label_info_item[3]
f.writelines("{} {} {} {} {}\n".format(0,center_x,center_y,small_width_scale,small_height_scale))
pass
创作分享不易,如果您觉得这篇blog对你有帮助,请留下一个免费的点赞,谢谢!