Ultralytics YOLO26におけるエンドツーエンド検出の理解
はじめに
YOLO26へのアップグレードを検討されている場合、YOLOv8やYOLO11といった以前のモデルからの最大の変更点の1つは、非最大値抑制(NMS)が削除されたことです。従来のYOLOモデルは数千の重複した予測を出力するため、最終的な検出結果に絞り込むには別途NMSのポストプロセッシングステップが必要でした。これはレイテンシを増加させ、エクスポートグラフを複雑にするだけでなく、ハードウェアプラットフォーム間で挙動に一貫性がなくなる可能性がありました。
YOLO26は異なるアプローチを採用しています。外部フィルタリングを必要とせず、最終的な検出結果をモデルから直接出力します。これは**エンドツーエンドの物体検出**として知られており、すべてのYOLO26モデルでデフォルトで有効になっています。その結果、デプロイメントパイプラインが簡素化され、レイテンシが低減し、CPUでの推論が最大43%高速化されます。
本ガイドでは、変更点、コードの更新が必要かどうか、どのエクスポートフォーマットがエンドツーエンド推論をサポートしているか、そして古いYOLOモデルからスムーズに移行する方法について解説します。
このアーキテクチャ変更の背景にある動機についての詳細は、YOLO26でNMSが削除された理由とそれがデプロイメントに与える影響に関するUltralyticsブログ記事をご覧ください。
- Ultralytics APIまたはCLIを使用していますか? 変更は不要です。モデル名を
yolo26n.ptに変更するだけです。 - Using custom inference code (ONNX Runtime, TensorRT, etc.)? Update your post-processing — detection output is now
(N, 300, 6)inxyxyformat, no NMS required. Other tasks append extra data (mask coefficients, keypoints, or angle). - エクスポートしますか? ほとんどのフォーマットはエンドツーエンド出力をネイティブでサポートしています。ただし、一部のフォーマット(NCNN、RKNN、PaddlePaddle、ExecuTorch、IMX、Edge TPU)は、サポートされていないオペレーター制約(
torch.topkなど)のため、自動的に従来の出力へフォールバックします。
エンドツーエンド検出の仕組み
YOLO26はトレーニング中にデュアルヘッドアーキテクチャを使用します。両方のヘッドは同じバックボーンとネックを共有しますが、異なる方法で出力を生成します。
| ヘッド | 目的 | 検出出力 | ポストプロセッシング |
|---|---|---|---|
| One-to-One(デフォルト) | エンドツーエンド推論 | (N, 300, 6) | 信頼度しきい値のみ |
| One-to-Many | 従来のYOLO出力 | (N, nc + 4, 8400) | NMSが必要 |
上記の形状は検出用です。他のタスクでは、検出ごとにデータを追加してOne-to-One出力を拡張します。
| タスク | エンドツーエンド出力 | 追加データ |
|---|---|---|
| 検出 | (N, 300, 6) | — |
| セグメンテーション | (N, 300, 6 + nm) + proto (N, nm, H, W) | nm マスク係数(デフォルト32) |
| 姿勢推定 | (N, 300, 57) | 17キーポイント × 3 (x, y, 可視性) |
| OBB | (N, 300, 7) | 回転角度 |
トレーニング中、両方のヘッドが同時に動作します。One-to-Manyヘッドはより豊富な学習シグナルを提供し、One-to-Oneヘッドは重複のないクリーンな予測を生成するように学習します。推論およびエクスポート中、デフォルトではOne-to-Oneヘッドのみがアクティブになり、画像あたり最大300個の検出結果を[x1, y1, x2, y2, confidence, class_id]の形式で出力します。
model.fuse()を呼び出すと、Conv + BatchNormレイヤーが統合されて推論が高速化されます。また、エンドツーエンドモデルではOne-to-Manyヘッドも削除され、モデルサイズとFLOPsが削減されます。デュアルヘッドアーキテクチャの詳細については、YOLO26モデルページを参照してください。
コードを変更する必要はありますか?
Ultralytics Python APIまたはCLIを使用している場合
変更は不要です。 標準のUltralytics Python APIやCLIを使用している場合、すべて自動的に機能します。予測、検証、エクスポートのすべてがエンドツーエンドモデルをそのまま処理します。
from ultralytics import YOLO
# Load a YOLO26 model
model = YOLO("yolo26n.pt")
# Predict — no NMS step, no code changes
results = model.predict("image.jpg")独自の推論コードを使用している場合
はい、出力形式が異なります。 YOLOv8やYOLO11向けに独自のポストプロセッシングロジックを記述していた場合(ONNX RuntimeやTensorRTで推論を実行する場合など)、新しい出力形状を処理するように更新する必要があります。
| YOLOv8 / YOLO11 | YOLO26 (エンドツーエンド) | |
|---|---|---|
| 検出出力 | (N, nc + 4, 8400) | (N, 300, 6) |
| ボックス形式 | xywh (中心x, 中心y, 幅, 高さ) | xyxy (左上x, 左上y, 右下x, 右下y) |
| レイアウト | ボックス座標 + アンカーごとのクラススコア | [x1, y1, x2, y2, conf, class_id] |
| NMSが必要 | はい | いいえ |
| ポストプロセッシング | NMS + 信頼度フィルタ | 信頼度フィルタのみ |
セグメンテーション、姿勢推定、OBBタスクの場合、YOLO26は各検出結果にタスク固有のデータを追加します。上記の出力形状テーブルを参照してください。
Nはバッチサイズ、ncはクラス数(COCOの場合は80など)です。
エンドツーエンドモデルを使用すると、ポストプロセッシングは非常にシンプルになります。例えばONNX Runtimeを使用する場合などがそうです。
import onnxruntime as ort
# Load and run the exported end-to-end model
session = ort.InferenceSession("yolo26n.onnx")
output = session.run(None, {session.get_inputs()[0].name: input_tensor})
# End-to-end output: (batch, 300, 6) → [x1, y1, x2, y2, confidence, class_id]
detections = output[0][0] # first image in batch
detections = detections[detections[:, 4] > conf_threshold] # confidence filter — that's it!One-to-Manyヘッドへの切り替え
従来のYOLO出力フォーマットが必要な場合(既存のNMSベースのポストプロセッシングコードを再利用する場合など)、end2end=Falseを設定することでいつでもOne-to-Manyヘッドに切り替えることができます。
from ultralytics import YOLO
model = YOLO("yolo26n.pt")
# Prediction with NMS (traditional behavior)
results = model.predict("image.jpg", end2end=False)
# Validation with NMS
metrics = model.val(data="coco.yaml", end2end=False)
# Export without end-to-end
model.export(format="onnx", end2end=False)エクスポートフォーマットの互換性
ほとんどのエクスポートフォーマットは、ONNX、TensorRT、CoreML、OpenVINO、TFLite、TF.js、MNNを含め、エンドツーエンド推論をそのままサポートしています。
以下のフォーマットはエンドツーエンドをサポートしておらず、自動的にOne-to-Manyヘッドにフォールバックします: NCNN、RKNN、PaddlePaddle、ExecuTorch、IMX、Edge TPU。
TensorRTはエンドツーエンドをサポートしていますが、TensorRT 10.3.0以下でint8=Trueを指定してエクスポートする場合は自動的に無効になります。
精度と速度のトレードオフ
エンドツーエンド検出は、精度への影響を最小限に抑えつつ、デプロイメントに大きなメリットをもたらします。
| 指標 | エンドツーエンド (デフォルト) | One-to-Many + NMS (end2end=False) |
|---|---|---|
| CPU推論速度 | 最大43%高速 | ベースライン |
| mAPへの影響 | ~0.5 mAP低下 | YOLO11と同等以上 |
| ポストプロセッシング | 信頼度フィルタのみ | 完全なNMSパイプライン |
| デプロイメントの複雑さ | 最小限 | NMSの実装が必要 |
ほとんどの実世界のアプリケーションにおいて、~0.5のmAPの違いは、速度と簡便性の向上を考慮すれば無視できる範囲です。最大の精度が最優先事項である場合は、end2end=Falseを使用していつでもOne-to-Manyヘッドにフォールバックできます。
すべてのモデルサイズ(n, s, m, l, x)のベンチマーク詳細については、YOLO26パフォーマンスメトリクスを参照してください。
YOLOv8またはYOLO11からの移行
既存のプロジェクトをYOLO26にアップグレードする場合、スムーズな移行のために以下のチェックリストを確認してください。
- Ultralytics API / CLIユーザー: 変更は不要です。モデル名を
yolo26n.pt(またはyolo26n-seg.pt、yolo26n-pose.pt、yolo26n-obb.pt)に更新するだけです。 - カスタムポストプロセッシングコード: 新しい出力形状(検出用の
(N, 300, 6)、およびセグメンテーション、姿勢推定、OBB用のタスク固有データ)を処理するように更新してください。また、ボックス形式がxywhからxyxyに変更された点にも注意してください。 - エクスポートパイプライン: ターゲットフォーマットについては、上記のフォーマットの互換性セクションを確認してください。
- TensorRT + INT8: エンドツーエンドサポートのためにTensorRTのバージョンが10.3.0より上であることを確認してください。
- FP16エクスポート: すべての出力をFP16にする必要がある場合は、
end2end=Falseでエクスポートしてください。output0がFP32のままになる理由を参照してください。 - iOS / CoreML: End-to-end is fully supported. If you need Xcode Preview support, use
end2end=Falsewithnms=True - エッジデバイス (NCNN, RKNN): これらのフォーマットは自動的にOne-to-Manyへフォールバックするため、デバイス上のパイプラインにNMSを含めてください。
FAQ
end2end=Trueとnms=Trueを同時に使用できますか?
No. These options are mutually exclusive. If you set nms=True on an end-to-end model during export, it will be automatically forced to nms=False with a warning. The end-to-end head already handles duplicate filtering internally, so external NMS is unnecessary.
ただし、end2end=Falseとnms=Trueを組み合わせた設定は有効であり、伝統的なNMSをエクスポートグラフに焼き込むことができます。これはCoreMLエクスポートにおいて、Xcodeのプレビュー機能で検出モデルを直接利用できるため便利です。
エンドツーエンドモデルにおけるmax_detパラメータは何を制御しますか?
max_detパラメータ(デフォルト: 300)は、One-to-Oneヘッドが画像あたりに出力できる検出結果の最大数を設定します。推論またはエクスポート時に調整可能です。
model.predict("image.jpg", max_det=100) # fewer detections, slightly faster
model.export(format="onnx", max_det=500) # more detections for dense scenesデフォルトのYOLO26チェックポイントはmax_det=300でトレーニングされていることに注意してください。この値を増やすことも可能ですが、One-to-Oneヘッドはトレーニング中に最大300個のクリーンな検出を生成するように最適化されているため、その制限を超える検出結果は品質が低下する可能性があります。画像あたり300個以上の検出が必要な場合は、より高いmax_det値での再トレーニングを検討してください。
エクスポートしたONNXモデルの出力が(1, 300, 6)になっていますが、これは正しいですか?
Yes, that's the expected end-to-end output format for detection: batch size of 1, up to 300 detections, each with 6 values [x1, y1, x2, y2, confidence, class_id]. Simply filter by confidence threshold and you're done — no NMS needed.
他のタスクでは出力形状が異なります。
| タスク | 出力形状 | 説明 |
|---|---|---|
| 検出 | (1, 300, 6) | [x1, y1, x2, y2, conf, class_id] |
| セグメンテーション | (1, 300, 38) + (1, 32, 160, 160) | 6つのボックス値 + 32個のマスク係数、およびプロトタイプマスクテンソル |
| 姿勢推定 | (1, 300, 57) | 6つのボックス値 + 17個のキーポイント × 3(x, y, 可視性) |
| OBB | (1, 300, 7) | 6つのボックス値 + 1つの回転角 |
エクスポートされたモデルがエンドツーエンドかどうかを確認するにはどうすればよいですか?
Ultralytics Python APIを使用するか、エクスポートされたONNXモデルのメタデータを直接確認することで調べることができます。
from ultralytics import YOLO
model = YOLO("yolo26n.onnx")
model.predict(verbose=False) # run predict to setup predictor first
print(model.predictor.model.end2end) # True if end-to-end is enabledあるいは、出力形状を確認してください。エンドツーエンドの検出モデルは (1, 300, 6) を出力し、従来のモデルは (1, nc + 4, 8400) を出力します。その他のタスクの形状については、出力形状のFAQ を参照してください。
セグメンテーション、ポーズ推定、OBBタスクでエンドツーエンドはサポートされていますか?
はい。すべてのYOLO26タスクバリエーション(検出、セグメンテーション、ポーズ推定、傾き物体検出 (OBB))は、デフォルトでエンドツーエンドの推論をサポートしています。すべてのタスクにおいて end2end=False のフォールバックも利用可能です。
各タスクは、基本的な検出出力にタスク固有のデータを拡張します。
| タスク | モデル | エンドツーエンド出力 |
|---|---|---|
| 検出 | yolo26n.pt | (N, 300, 6) |
| セグメンテーション | yolo26n-seg.pt | (N, 300, 38) + proto (N, 32, 160, 160) |
| 姿勢推定 | yolo26n-pose.pt | (N, 300, 57) |
| OBB | yolo26n-obb.pt | (N, 300, 7) |