【实例分割】转换YOLO格式标注至COCO格式JSON

这段代码定义了一个函数,用于将由YOLO生成的文本标签文件转换为MMdet所需的JSON格式,以便于实例分割任务。它处理每个图像中的对象坐标、面积和边界框,并将它们组织成符合MMdet要求的JSON结构。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

yolo2coco代码:

import json
import glob
import os
import cv2
import matplotlib.pyplot as plt
from matplotlib.patches import Polygon
from PIL import Image, ImageDraw, ImageFont
import numpy as np


def calculate_polygon_area(polygon):
    x = polygon[:, 0]
    y = polygon[:, 1]
    return 0.5 * np.abs(np.dot(x, np.roll(y, 1)) - np.dot(y, np.roll(x, 1)))


def calculate_bounding_box(polygon):
    x_min = np.min(polygon[:, 0])
    y_min = np.min(polygon[:, 1])
    x_max = np.max(polygon[:, 0])
    y_max = np.max(polygon[:, 1])
    width = x_max - x_min
    height = y_max - y_min
    return [x_min, y_min, width, height]


def text_to_json_segmentation(in_labels, in_images, out_json):
    """
    Convert instance segmentation dataset from text files generated by the function 'json_to_text_segmentation'
    (for YOLO) to a JSON file (for MMdet). This can be applied for Level 0/1/2 (must modify the last code)
    :param in_labels: input folder containing the label text files
    :param in_images: input folder containing the image files (just for getting the image size)
    :param out_json: output JSON file
    """
    # Initialize the output JSON file
    data = dict()
    data['annotations'] = []
    data['images'] = []

    # Initial the number of annotations
    num_annotations = 1  # index starts from 1

    # Process the text files
    txt_files = glob.glob(in_labels + '/*.txt')
    for k in range(len(txt_files)):
        # Read the image to get image width and height
        img = Image.open(in_images + '/' + os.path.basename(txt_files[k]).replace('txt', 'jpg'))
        image_width, image_height = img.size

        # Creates annotation items of the image and append them to the list
        with open(txt_files[k]) as f:
            for line in f:
                # Get annotation information of each line in the text file
                line = [float(x) for x in line.strip().split()]
                class_id = int(line[0]) + 1  # index starts from 1
                coordinates = line[1:]
                polygon = np.array(coordinates).reshape(-1, 2)
                polygon[:, 0] = polygon[:, 0] * image_width
                polygon[:, 1] = polygon[:, 1] * image_height

                area = calculate_polygon_area(polygon)
                bbox = calculate_bounding_box(polygon)

                # Create a new annotation item
                ann_item = dict()
                ann_item['segmentation'] = [polygon.flatten().tolist()]
                ann_item['area'] = area
                ann_item['iscrowd'] = 0
                ann_item['image_id'] = k + 1  # index starts from 1
                ann_item['bbox'] = bbox
                ann_item['category_id'] = class_id
                ann_item['id'] = num_annotations
                data['annotations'].append(ann_item)
                num_annotations += 1

        # Create a new image item and append it to the list
        img_item = dict()
        img_item['id'] = k + 1  # index starts from 1
        img_item['file_name'] = os.path.basename(txt_files[k]).replace('txt', 'jpg')
        img_item['height'] = image_height
        img_item['width'] = image_width
        data['images'].append(img_item)

        print(os.path.basename(txt_files[k]) + ' done')

    data['categories'] = [{'supercategory': 'class1', 'id': 1, 'name': 'class1'}]

    # Write the dictionary to a JSON file
    print('Writing the data to a JSON file')
    with open(out_json, 'w') as f:
        # json.dump(data, f, cls=NpEncoder)
        # f.write(json.dumps(data, cls=NpEncoder, indent=4))
        f.write(json.dumps(data, default=int, indent=4))



if __name__ == '__main__':
    # Convert the segmentation text files to JSON 
    text_to_json_segmentation(in_labels='labels/test',
                              in_images='images/test',
                              out_json='instances_test2017.json')

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值