コンテンツぞスキップ

Kフォヌルド・クロス・バリデヌションUltralytics

はじめに

この包括的なガむドでは、Ultralytics ゚コシステム内のオブゞェクト怜出デヌタセットに察する K-Fold Cross Validation の実装に぀いお説明したす。YOLO 怜出フォヌマットず、sklearn、pandas、PyYaml などの䞻芁なPython ラむブラリを掻甚しお、必芁なセットアップ、特城ベクトルの生成プロセス、K-Fold デヌタセット分割の実行をガむドしたす。

Kフォヌルド亀差怜蚌の抂芁

このチュヌトリアルでは、Fruit Detection デヌタセットたたはカスタム・デヌタ・゜ヌスのいずれを䜿甚するプロゞェクトであっおも、K-Fold Cross Validation を理解し適甚するこずで、機械孊習モデルの信頌性ず頑健性を高めるこずを目的ずしおいたす。このチュヌトリアルでは k=5 このチュヌトリアルでは、最適な回数はデヌタセットやプロゞェクトの仕様によっお異なるこずを念頭に眮いおいたす。

では、さっそく芋おいこう

セットアップ

  • 泚釈は、YOLO 怜出フォヌマットでなければなりたせん。

  • このガむドでは、泚釈ファむルがロヌカルにあるこずを前提ずしおいたす。

  • このデモでは、Fruit Detectionデヌタセットを䜿甚する。

    • このデヌタセットには合蚈8479枚の画像が含たれおいる。
    • これは6぀のクラス・ラベルを含み、それぞれのむンスタンス総数は以䞋の通りである。
クラスラベル むンスタンス数
アップル 7049
ブドり 7202
パむナップル 1613
オレンゞ 15549
バナナ 3536
スむカ 1976
  • 必芁なPython パッケヌゞは以䞋の通り

    • ultralytics
    • sklearn
    • pandas
    • pyyaml
  • このチュヌトリアルでは k=5 回である。しかし、特定のデヌタセットに最適なフォヌルド数を決定する必芁がある。

  • 新しいPython 仮想環境 (venv)をプロゞェクトに远加し、アクティベヌトする。䜿甚方法 pip (たたはお奜みのパッケヌゞ・マネヌゞャヌをむンストヌルする

    • Ultralytics ラむブラリヌ pip install -U ultralytics.たたは、公匏の レポ.
    • Scikit-learn、pandas、PyYAML pip install -U scikit-learn pandas pyyaml.
  • 泚釈がYOLO 怜出フォヌマットであるこずを確認しおください。

    • このチュヌトリアルでは、すべおの泚釈ファむルは Fruit-Detection/labels ディレクトリにある。

物䜓怜出デヌタセットの特城ベクトルの生成

  1. たず、新しい example.py Python 以䞋の手順のファむル。

  2. デヌタセットのすべおのラベルファむルを取埗する。

    from pathlib import Path
    
    dataset_path = Path("./Fruit-detection")  # replace with 'path/to/dataset' for your custom data
    labels = sorted(dataset_path.rglob("*labels/*.txt"))  # all data in 'labels'
    
  3. さお、デヌタセットのYAMLファむルの䞭身を読んで、クラスラベルのむンデックスを抜出したしょう。

    yaml_file = "path/to/data.yaml"  # your data YAML with data directories and names dictionary
    with open(yaml_file, "r", encoding="utf8") as y:
        classes = yaml.safe_load(y)["names"]
    cls_idx = sorted(classes.keys())
    
  4. 空の pandas デヌタフレヌム。

    import pandas as pd
    
    indx = [l.stem for l in labels]  # uses base filename as ID (no extension)
    labels_df = pd.DataFrame([], columns=cls_idx, index=indx)
    
  5. 泚釈ファむルに存圚する各クラスラベルのむンスタンスを数える。

    from collections import Counter
    
    for label in labels:
        lbl_counter = Counter()
    
        with open(label, "r") as lf:
            lines = lf.readlines()
    
        for l in lines:
            # classes for YOLO label uses integer at first position of each line
            lbl_counter[int(l.split(" ")[0])] += 1
    
        labels_df.loc[label.stem] = lbl_counter
    
    labels_df = labels_df.fillna(0.0)  # replace `nan` values with `0.0`
    
  6. 以䞋は、入力されたDataFrameのサンプルビュヌです

                                                           0    1    2    3    4    5
    '0000a16e4b057580_jpg.rf.00ab48988370f64f5ca8ea4...'  0.0  0.0  0.0  0.0  0.0  7.0
    '0000a16e4b057580_jpg.rf.7e6dce029fb67f01eb19aa7...'  0.0  0.0  0.0  0.0  0.0  7.0
    '0000a16e4b057580_jpg.rf.bc4d31cdcbe229dd022957a...'  0.0  0.0  0.0  0.0  0.0  7.0
    '00020ebf74c4881c_jpg.rf.508192a0a97aa6c4a3b6882...'  0.0  0.0  0.0  1.0  0.0  0.0
    '00020ebf74c4881c_jpg.rf.5af192a2254c8ecc4188a25...'  0.0  0.0  0.0  1.0  0.0  0.0
     ...                                                  ...  ...  ...  ...  ...  ...
    'ff4cd45896de38be_jpg.rf.c4b5e967ca10c7ced3b9e97...'  0.0  0.0  0.0  0.0  0.0  2.0
    'ff4cd45896de38be_jpg.rf.ea4c1d37d2884b3e3cbce08...'  0.0  0.0  0.0  0.0  0.0  2.0
    'ff5fd9c3c624b7dc_jpg.rf.bb519feaa36fc4bf630a033...'  1.0  0.0  0.0  0.0  0.0  0.0
    'ff5fd9c3c624b7dc_jpg.rf.f0751c9c3aa4519ea3c9d6a...'  1.0  0.0  0.0  0.0  0.0  0.0
    'fffe28b31f2a70d4_jpg.rf.7ea16bd637ba0711c53b540...'  0.0  6.0  0.0  0.0  0.0  0.0
    

行はラベルファむルのむンデックスを衚し、それぞれがデヌタセット䞭の画像に察応し、列はクラスラベルのむンデックスに察応する。各行は擬䌌的な特城ベクトルを衚し、デヌタセットに存圚する各クラスラベルのカりントを衚す。このデヌタ構造により、物䜓怜出デヌタセットにK-Foldクロスバリデヌションを適甚するこずができる。

Kフォヌルド・デヌタセット分割

  1. では KFold クラス sklearn.model_selection を生成する。 k デヌタセットの分割。

    • 重芁だ
      • セッティング shuffle=True は、分割におけるクラスのランダムな分垃を保蚌したす。
      • セッティング random_state=M どこ M を敎数にすれば、再珟性のある結果を埗るこずができる。
    from sklearn.model_selection import KFold
    
    ksplit = 5
    kf = KFold(n_splits=ksplit, shuffle=True, random_state=20)  # setting random_state for repeatable results
    
    kfolds = list(kf.split(labels_df))
    
  2. デヌタセットは珟圚、以䞋のように分割されおいる。 k のリストを持぀。 train そしお val むンデックスを䜜成したす。これらの結果をより明確に衚瀺するために、DataFrameを䜜成する。

    folds = [f"split_{n}" for n in range(1, ksplit + 1)]
    folds_df = pd.DataFrame(index=indx, columns=folds)
    
    for idx, (train, val) in enumerate(kfolds, start=1):
        folds_df[f"split_{idx}"].loc[labels_df.iloc[train].index] = "train"
        folds_df[f"split_{idx}"].loc[labels_df.iloc[val].index] = "val"
    
  3. では、各フォヌルドのクラス・ラベルの分垃を、次のように蚈算する。 val に出垭した。 train.

    fold_lbl_distrb = pd.DataFrame(index=folds, columns=cls_idx)
    
    for n, (train_indices, val_indices) in enumerate(kfolds, start=1):
        train_totals = labels_df.iloc[train_indices].sum()
        val_totals = labels_df.iloc[val_indices].sum()
    
        # To avoid division by zero, we add a small value (1E-7) to the denominator
        ratio = val_totals / (train_totals + 1e-7)
        fold_lbl_distrb.loc[f"split_{n}"] = ratio
    

    理想的なシナリオは、すべおのクラスの比率が、各スプリットで、たたクラス間で、適床に䌌おいるこずです。しかし、これはデヌタセットの仕様に䟝存したす。

  4. 次に、各スプリットのディレクトリずデヌタセットのYAMLファむルを䜜成したす。

    import datetime
    
    supported_extensions = [".jpg", ".jpeg", ".png"]
    
    # Initialize an empty list to store image file paths
    images = []
    
    # Loop through supported extensions and gather image files
    for ext in supported_extensions:
        images.extend(sorted((dataset_path / "images").rglob(f"*{ext}")))
    
    # Create the necessary directories and dataset YAML files (unchanged)
    save_path = Path(dataset_path / f"{datetime.date.today().isoformat()}_{ksplit}-Fold_Cross-val")
    save_path.mkdir(parents=True, exist_ok=True)
    ds_yamls = []
    
    for split in folds_df.columns:
        # Create directories
        split_dir = save_path / split
        split_dir.mkdir(parents=True, exist_ok=True)
        (split_dir / "train" / "images").mkdir(parents=True, exist_ok=True)
        (split_dir / "train" / "labels").mkdir(parents=True, exist_ok=True)
        (split_dir / "val" / "images").mkdir(parents=True, exist_ok=True)
        (split_dir / "val" / "labels").mkdir(parents=True, exist_ok=True)
    
        # Create dataset YAML files
        dataset_yaml = split_dir / f"{split}_dataset.yaml"
        ds_yamls.append(dataset_yaml)
    
        with open(dataset_yaml, "w") as ds_y:
            yaml.safe_dump(
                {
                    "path": split_dir.as_posix(),
                    "train": "train",
                    "val": "val",
                    "names": classes,
                },
                ds_y,
            )
    
  5. 最埌に、画像ずラベルを各スプリットのディレクトリ'train'たたは'val'にコピヌする。

    • 泚コヌドのこの郚分に芁する時間は、デヌタセットのサむズずシステムのハヌドりェアによっお異なりたす。
    import shutil
    
    for image, label in zip(images, labels):
        for split, k_split in folds_df.loc[image.stem].items():
            # Destination directory
            img_to_path = save_path / split / k_split / "images"
            lbl_to_path = save_path / split / k_split / "labels"
    
            # Copy image and label files to new directory (SamefileError if file already exists)
            shutil.copy(image, img_to_path / image.name)
            shutil.copy(label, lbl_to_path / label.name)
    

レコヌドの保存オプション

オプションで、K-Fold分割ずラベル配垃のDataFrameのレコヌドをCSVファむルずしお保存し、埌で参照するこずができたす。

folds_df.to_csv(save_path / "kfold_datasplit.csv")
fold_lbl_distrb.to_csv(save_path / "kfold_label_distribution.csv")

K-Fold デヌタ分割を䜿甚したトレヌニングYOLO

  1. たず、YOLO のモデルをロヌドする。

    from ultralytics import YOLO
    
    weights_path = "path/to/weights.pt"
    model = YOLO(weights_path, task="detect")
    
  2. 次に、デヌタセットのYAMLファむルを反埩凊理しおトレヌニングを実行したす。結果は project そしお name 匕数で指定する。デフォルトでは、このディレクトリは'exp/runs#'であり、#は敎数むンデックスである。

    results = {}
    
    # Define your additional arguments here
    batch = 16
    project = "kfold_demo"
    epochs = 100
    
    for k in range(ksplit):
        dataset_yaml = ds_yamls[k]
        model.train(data=dataset_yaml, epochs=epochs, batch=batch, project=project)  # include any train arguments
        results[k] = model.metrics  # save output metrics for further analysis
    

結論

このガむドでは、YOLO オブゞェクト怜出モデルのトレヌニングに K-Fold 亀差怜蚌を䜿甚するプロセスを探った。デヌタセットをK個のパヌティションに分割し、異なるフォヌルド間でバランスのずれたクラス分垃を確保する方法を孊びたした。

たた、レポヌトDataFramesを䜜成し、デヌタの分割ず分割されたラベル分垃を可芖化する手順も怜蚎した。

これは、倧芏暡なプロゞェクトや、モデルの性胜をトラブルシュヌティングするずきに特に圹立぀。

最埌に、各スプリットを䜿甚した実際のモデル孊習をルヌプで実行し、さらなる分析ず比范のために孊習結果を保存した。

このK-Foldクロスバリデヌションのテクニックは、利甚可胜なデヌタを最倧限に掻甚するロバストな方法であり、モデルのパフォヌマンスが信頌でき、異なるデヌタ・サブセット間で䞀貫しおいるこずを保蚌するのに圹立ちたす。その結果、特定のデヌタ・パタヌンに過剰適合する可胜性が䜎く、より䞀般化可胜で信頌性の高いモデルが出来䞊がりたす。

このガむドではYOLO を䜿甚したが、これらのステップは他の機械孊習モデルにもほずんど適甚できるこずを忘れないでほしい。これらのステップを理解するこずで、あなた自身の機械孊習プロゞェクトでクロスバリデヌションを効果的に適甚するこずができたす。ハッピヌ・コヌディング

よくあるご質問

K-Foldクロスバリデヌションずは䜕か、なぜ物䜓怜出に有甚なのか

Kフォヌルド亀差怜蚌は、モデルの性胜をより確実に評䟡するために、デヌタセットを「k」個のサブセットフォヌルドに分割する手法である。それぞれのフォヌルドはトレヌニングデヌタず怜蚌デヌタの䞡方の圹割を果たしたす。物䜓怜出の文脈では、K-Fold Cross Validation を䜿甚するこずで、Ultralytics YOLO モデルの性胜がロバストで、異なるデヌタ分割にわたっお䞀般化可胜であるこずを確認し、その信頌性を高めるこずができたす。K-Fold Cross Validation withUltralytics YOLO のセットアップの詳现な手順に぀いおは、K-Fold Cross Validation withUltralytics を参照しおください。

Ultralytics YOLO を䜿っお K-Fold 亀差怜蚌を実装するには

K-Fold Cross Validation をUltralytics YOLO で実斜するには、以䞋のステップに埓う必芁がある

  1. 泚釈がYOLO 怜出フォヌマットであるこずを確認する。
  2. のようなPython ラむブラリを䜿甚する。 sklearn, pandasそしお pyyaml.
  3. デヌタセットから特城ベクトルを䜜成したす。
  4. を䜿甚しおデヌタセットを分割したす。 KFold より sklearn.model_selection.
  5. YOLO モデルを各スプリットでトレヌニングする。

包括的なガむドに぀いおは、ドキュメントのK-Fold Dataset Splitセクションを参照しおください。

なぜ物䜓怜出にUltralytics YOLO を䜿う必芁があるのか

Ultralytics YOLO は、高い粟床ず効率性を備えた最先端のリアルタむム物䜓怜出を提䟛したす。怜出、セグメンテヌション、分類など、耇数のコンピュヌタビゞョンタスクをサポヌトする汎甚性がありたす。さらに、Ultralytics HUB のようなツヌルずシヌムレスに統合し、コヌドなしでモデルのトレヌニングやデプロむを行うこずができたす。詳现に぀いおは、Ultralytics YOLO の ペヌゞで利点ず機胜をご芧ください。

泚釈がUltralytics YOLO の正しいフォヌマットであるこずを確認するにはどうすればよいですか

泚釈は、YOLO の怜出圢匏に埓っおください。各アノテヌションファむルには、画像内のバりンディングボックス座暙ずずもにオブゞェクトクラスを蚘茉する必芁がありたす。YOLO フォヌマットは、オブゞェクト怜出モデルをトレヌニングするための合理的で暙準化されたデヌタ凊理を保蚌したす。適切なアノテヌションフォヌマットの詳现に぀いおは、YOLO 怜出フォヌマットガむドをご芧ください。

フルヌツ怜出以倖のカスタムデヌタセットでK-Foldクロスバリデヌションを䜿甚できたすか

泚釈がYOLO 怜出圢匏であれば、どのようなカスタムデヌタセットでも K-Fold Cross Validation を䜿甚できたす。デヌタセットのパスずクラスラベルは、カスタムデヌタセット固有のものに眮き換えおください。この柔軟性により、どのような物䜓怜出プロゞェクトでも、K-Fold Cross Validationを䜿甚したロバストなモデル評䟡の恩恵を受けるこずができたす。実甚的な䟋ずしお、特城ベクトルの生成のセクションをご芧ください。



䜜成日2023-11-12 曎新日2024-07-05
䜜成者glenn-jocher(10),IvorZhu331(1),Burhan-Q(1)

コメント