VoTTでアノテーションしたファイルをyolo形式に変換する方法

こんにちは!

とびろぐ管理人のとびうおです!

今回は、VoTTでアノテーションしたファイルをyolo形式に変換する方法にを解説します!

pythonコードで変換する

個人的には、pythonコードを用いて変換してしまうのが一番おすすめです。

サンプルコードを記述しておきます!

コメントアウトでの解説箇所の部分を改造していけば、ご自身のものに対応できます!

import json
import os

# タグをクラスIDにマッピングする辞書
class_mapping = {
    "cat": 0,
    "dog": 1,
}

# JSONファイルがあるディレクトリを指定
json_directory = '/path/to/your/json/files'

# 出力ディレクトリ
output_dir = '/path/to/your/json/files'

# 指定されたディレクトリ内の全てのJSONファイルを処理
for json_filename in os.listdir(json_directory):
    if json_filename.endswith('.json'):
        json_file_path = os.path.join(json_directory, json_filename)

        # JSONファイルを読み込む
        with open(json_file_path, 'r') as file:
            data = json.load(file)

        img_width = data['asset']['size']['width']
        img_height = data['asset']['size']['height']
        image_filename = os.path.splitext(data['asset']['name'])[0]

        yolo_data = []
        for region in data['regions']:
            # 各タグに対する処理
            for tag in region['tags']:
                class_id = class_mapping.get(tag)
                if class_id is not None:
                    x_left = region['boundingBox']['left']
                    y_top = region['boundingBox']['top']
                    box_width = region['boundingBox']['width']
                    box_height = region['boundingBox']['height']

                    x_center = (x_left + box_width / 2) / img_width
                    y_center = (y_top + box_height / 2) / img_height
                    width = box_width / img_width
                    height = box_height / img_height

                    yolo_data.append(f"{class_id} {x_center} {y_center} {width} {height}")

        # YOLO形式のデータをテキストファイルに保存
        output_file_path = os.path.join(output_dir, f"{image_filename}.txt")
        with open(output_file_path, 'w') as file:
            file.write('\n'.join(yolo_data))

        print(f'YOLO形式のデータが {output_file_path} に保存されました。')

print('全てのJSONファイルの処理が完了しました。')
とびうおくん
とびうおくん

このコードをそのまま貼り付けても動かないので
ディレクトリ名等をご自身のものに変更してください!

クラスマッピングを修正する

まず、class_mapping辞書については、アノテーションされたタグにしないといけないので、そこを修正していく必要があります。

例えば、”cup”や”table”でアノテーションしたのであれば左のファイルを右のようにする必要があります。

# タグをクラスIDにマッピングする辞書
class_mapping = {
    "cat": 0,
    "dog": 1,
}
# タグをクラスIDにマッピングする辞書
class_mapping = {
    "cup": 0,
    "table": 1,
}
とびうおくん
とびうおくん

yoloはタグの名前ではなく

0,1なので、このように変更する必要があります

ファイルがある/出力ディレクトリを修正

ファイルが存在しているディレクトリと出力するべきディレクトリを変更する必要があります。

おすすめは フルパス で指定することです!

# JSONファイルがあるディレクトリを指定
json_directory = '/path/to/your/json/files'

# 出力ディレクトリ
output_dir = '/path/to/your/json/files'
とびうおくん
とびうおくん

同じディレクトリにするとバグるので

専用のファイルにしましょう!

Pythonファイルの解説

簡単にこのPythonスクリプトが行っていることの解説をしていきます。

クラスマッピングを定義

class_mapping 辞書は、アノテーションされたタグ(例えば “cat”, “dog”)を、YOLOが理解できる数値のクラスIDに変換します。

これにより、異なる種類のオブジェクトを区別できるようになります。

JSONファイルの処理

次に、スクリプトがどのようにJSONファイルを読み込み、画像のサイズ情報を取得するかを説明します。

この部分は、バウンディングボックスを正確に計算するために重要です。

バウンディングボックスの変換

バウンディングボックスのデータ(左上の座標、幅、高さ)をYOLO形式に変換するプロセスについて詳しく説明します。

YOLO形式では、バウンディングボックスは画像の幅と高さに対する相対的な中心座標とサイズで表されます。

テキストファイルへの出力

変換されたデータをどのようにテキストファイルに書き込むかを説明します。

各行が一つのオブジェクトを表し、クラスIDとバウンディングボックスの情報が含まれていることを強調します。

まとめ

VoTT→yolo形式にするにはいろいろなツールがありますが、個人的にはpythonコードを書いてしまった方が便利、かつカスタマイズもしやすいうえに安全かなと思っています!

何かの変換や移動にはPythonは非常に強いので、ぜひコードを書いてやってみましょう!

とびうおくん
とびうおくん

1000枚くらいが
一気に処理されていくのは
非常に気持ちよいです!

とびうお
ブログ管理人です!
swimaneというアプリをリリースしました!

コメント

タイトルとURLをコピーしました