YOLOv8を使ってスプラトゥーン3で敵を検出してみた。

皆さん、スプラトゥーンは好きですか？私はスプラトゥーンが好きでほぼ毎日やってます。そんなとき、「AIで敵を検出できたら面白そうだな」と思いました。てなわけで2023年1月に出たYOLOv8を使って、スプラトゥーン3で敵を検出するモデルを作ってみました。

## 使用したもの
* labelImg
* google colaboratory
* YOLOv8
* 訓練データ888枚 ＋ ラベルデータ
* 検証データ208枚 ＋ ラベルデータ
* テストデータ100枚

フォルダー構成は以下のようにしました。↓
```
objectdetection/
    └detection.yaml
    ├train/
        └image.png
        └label.txt
    ├val/
        └image.png
        └label.txt
    ├test/
        └image.png
```
## アノテーション
まず初めに訓練データをたくさん集めてlabelImgを使ってアノテーションしていきます。labelImgとは画像に写っている学習させたい検出物を四角で囲ってラベルを作成するツールのことです。四角で囲った部分の座標がテキストドキュメントとして保存されるようになっています。今回は検証データも用意してあるのでそちらにもアノテーションしていきます。
labelImgのインストール方法は以下のサイトを参考にしました。↓
https://www.tankobucreate.com/labelimg_install/
こんな感じでアノテーションしていきます。↓
![「YOLOv8を使ってスプラトゥーン3で敵を検出してみた。」を編集 - Qiita - Google Chrome 2023_02_23 17_21_41.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/a339c033-464f-89fa-aac0-c0eb4edc67a8.png)

## labelImg
labelImgの使い方は簡単です。「Open Dir」を押して使用する画像が保存されているディレクトリを選択します。
![スクショ１.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/b3b6431c-875b-c489-5889-4281ff4fb5d3.png)
「Change Save Dir」を押してアノテーションした場所の座標を保存するディレクトリを選択します。
![スクショ２.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/fa829ea3-7711-bbd6-0a3b-a55d90200fc4.png)
※YOLOの事前学習モデルを使用する場合は下の画像の赤線で囲ってある所を「YOLO」にしてください。
![「YOLOv8を使ってスプラトゥーン3で敵を検出してみた。」を編集 - Qiita - Google Chrome 2023_02_23 17_21_41.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/abd2c356-efe7-6016-a00c-7bf3e26603b3.png)
ヘッダーの「view」を開くと一番上に「Auto Save Mode」があるのでそれを押すと、自動で保存されるようになります。
![スクショ５.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/24626f83-bfa9-ea7d-036d-f12dc6b3c36d.png)
以下のように選択されたディレクトリにアノテーションの座標がテキストファイルで保存されます。
![スクショ３.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/01557505-879c-3bbe-99f9-c64a5c77f1fc.png)
保存されたテキストファイルはこんな感じです。
![IMG_1268 - メモ帳 2023_02_24 16_42_41.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/9c3a8c13-2d02-1609-1c79-ec1ceeed6d5b.png)


画像へのアノテーションが終わったら、その画像と座標が入力されているテキストファイルをgoogle driveにアップロードします。
それとyamlファイルが必要なのでそれも作成していきます。私は以下のようにVScodeで作成しました。↓
![detection.yaml - Visual Studio Code 2023_02_23 18_58_55.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/4aaa92dc-b3f0-8862-d337-aecd84a778a5.png)
* 「nc」には検出したい物の数を入力します。今回は敵だけを検出したいので「1」と入力しています。
* 「names」には検出したい物の名前を入力します。

## 学習
それでは学習に入ります。まず、yolov8をインストールしていきます。
```
!git clone https://github.com/ultralytics/ultralytics
%cd ultralytics
!pip install -r requirements.txt
```
次に以下のようにすれば学習が開始されます。学習が終わると一番精度が良いパラメーター（best.pt）が/content/ultralytics/runs/detect/train/weightsに自動で保存されるようになっています。
```
from ultralytics import YOLO

model = YOLO("yolov8m.pt")

results = model.train(data="ここには先ほど作成したyamlファイルパスを入力", epochs=200, batch=20, imgsz=1280, rect=True)
results = model.val()
```
以下のように学習が進んでいきます。
※google colaboratoryを使うときは有料版にしないとメモリ不足で学習できなくなります。
```
Epoch    GPU_mem   box_loss   cls_loss   dfl_loss  Instances       Size
      1/200      18.5G      2.204      3.967      1.859          8       1280: 100%|██████████| 45/45 [01:30<00:00,  2.02s/it]
                 Class     Images  Instances      Box(P          R      mAP50  mAP50-95): 100%|██████████| 6/6 [00:53<00:00,  8.95s/it]
                   all        208        281      0.348       0.27      0.223     0.0894

      Epoch    GPU_mem   box_loss   cls_loss   dfl_loss  Instances       Size
      2/200      21.7G      2.123      2.638      1.953          9       1280: 100%|██████████| 45/45 [00:15<00:00,  2.87it/s]
                 Class     Images  Instances      Box(P          R      mAP50  mAP50-95): 100%|██████████| 6/6 [00:04<00:00,  1.25it/s]
                   all        208        281    0.00926      0.342    0.00544     0.0022

      Epoch    GPU_mem   box_loss   cls_loss   dfl_loss  Instances       Size
      3/200      21.7G      2.261      2.646      2.101          9       1280: 100%|██████████| 45/45 [00:15<00:00,  2.94it/s]
                 Class     Images  Instances      Box(P          R      mAP50  mAP50-95): 100%|██████████| 6/6 [00:04<00:00,  1.20it/s]
                   all        208        281      0.299      0.221      0.151     0.0557
```

## 結果は...？
学習が終わったらテストデータでモデルを試します。
/content/ultralytics/runs/detect/train/weightsに保存されたbest.ptを使います。その結果が以下の画像になります。
```
model = YOLO("/content/ultralytics/runs/detect/train/weights/best.pt")
results = model.predict(source="用意したテストデータ", data="yamlファイルパス", save=True, imgsz=1280, rect=True)
```
![IMG_2428.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/d0019f00-004d-e7f2-757f-7f9b485b4a66.png)
![IMG_2327.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/d50eff7b-d9b6-9400-db65-bde359cd3c5e.png)
![IMG_2166.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/8330a4b0-7a8b-3347-5f75-e42f908ceb3d.png)
![IMG_2158.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/571f516c-3267-7d69-a290-7c05f23e4293.png)
![IMG_2104.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/9ce80e0d-4f96-8e67-cf4b-9aa0f721781b.png)
![IMG_2069 (1).PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/92479e1f-826c-6c42-6bca-c302ce56b74e.png)
![IMG_2077.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3073852/9c4939ae-d916-1984-2ce3-ce6328227109.png)
## まとめ
今回、yolov8を使ってスプラトゥーン3で敵検出をやってみましたが、ちゃんと近くにいる敵や遠くにいる敵を検出出来ていたり、誤検出やそもそも検出しなかったりなどバラつきがありました。しかもまだ動画では試したことがないので動画でも試してみようと思います。また、何かアドバイスがあれば教えていただけると嬉しいです。