YOLO-NAS

Ein konvolutionaler Detektor, dessen Backbone und Neck aus der Architektursuche von Deci.AI hervorgingen und auf quantisierungsbewussten RepVGG-Blöcken basieren. Die Gewichte stammen von Deci.AI und sind nur für die nicht kommerzielle Nutzung lizenziert. LibreYOLO veröffentlicht keine davon.

Aufgaben
detection, pose, oriented boxes
Größen
s, m, l at 640 px
Installation
pip install libreyolo
Supportstufe
Kern, seit v1.1.0. Trainierbare Kerndetektoren: Funktionen folgen den Flaggschiffen in derselben Release-Welle.
Upstream
YOLO-NAS von Deci.AI, Deci.AI proprietary, non-commercial. Publikation, Quelle
Lizenzen
Code Apache-2.0, Gewichte Deci.AI proprietary, non-commercial. Kommerzielle Nutzung

Installation

YOLO-NAS benötigt neben dem Basispaket kein zusätzliches Extra.

bash
pip install libreyolo

Vorhersage

Ein Checkpoint-Name, der noch nicht lokal vorliegt, wird von Decis öffentlichem CDN und nicht von der LibreYOLO-Organisation geladen, da diese keine solchen Gewichte hostet. Vor Beginn der Übertragung zeigt die Bibliothek Decis Lizenzbedingungen einmal pro Prozess an. Bevor die heruntergeladene Datei geöffnet wird, prüft sie deren SHA-256 gegen einen fest hinterlegten Wert. Welche Nutzung diese Bedingungen erlauben, steht unter Lizenzierung.

Python
from libreyolo import LibreYOLO, SAMPLE_IMAGE # Ein Name, der noch nicht lokal vorliegt, wird von Decis CDN geladen.# Vor dem Download werden Decis Lizenzbedingungen angezeigt; mit dem Herunterladen akzeptierst du sie.model = LibreYOLO("LibreYOLONASs.pt")result = model(SAMPLE_IMAGE, save=True) for box in result.boxes:    print(box.cls, box.conf, box.xyxy)
CLI
libreyolo predict model=LibreYOLONASs.pt save=True \  source=https://raw.githubusercontent.com/LibreYOLO/libreyolo/release/libreyolo/assets/parkour.jpg
Posenschätzung
from libreyolo import LibreYOLO, SAMPLE_IMAGE # Das Suffix -pose wählt den Pose-Kopf und dessen eigenen Gewichtssatz aus.model = LibreYOLO("LibreYOLONASs-pose.pt")result = model(SAMPLE_IMAGE) print(result.keypoints.xy)

Das zurückgegebene Results-Objekt entspricht dem jeder anderen Familie, sodass der Wechsel zu einem anderen Detektor nur eine einzige Codezeile erfordert. conf legt den Konfidenzschwellenwert und iou den NMS-Schwellenwert fest. Unter Vorhersage findest du Informationen zu Quellen, Streaming und Ergebnisverarbeitung.

Die Aufgabe für orientierte Boxen liefert result.obb. Der veröffentlichte OBB-Graph verwendet eine Bildfläche von 1024 Pixeln und seinen gespeicherten Satz von 18 Klassenlabels.

Varianten

Objekterkennung und Posenschätzung verwenden dieselbe Architektur mit unterschiedlichen Köpfen und akzeptieren dieselben Argumente. Die Größen in der folgenden Tabelle gehören zur Objekterkennung. Für die Posenschätzung ist zusätzlich eine kleinere Größe verfügbar. Der Pose-Kopf sagt den COCO-Keypoint-Satz vorher.

CheckpointEingabe (px)mAP 50-95Parameter (M)
LibreYOLONASl64056.366.98
LibreYOLONASm64055.451.18
LibreYOLONASs64051.819.05

COCO val2017, 500 images. Gemessen mit dem LibreYOLO-Benchmarksystem und auf Vision Analysis veröffentlicht. Dort werden Latenzen verschiedener Hardware und Runtimes verglichen und die vollständigen Laufprotokolle bereitgestellt.

Training

Python
from libreyolo import LibreYOLO model = LibreYOLO("LibreYOLONASs.pt")model.train(data="my-dataset.yaml", epochs=100, imgsz=640, batch=16)
CLI
libreyolo train model=LibreYOLONASs.pt data=my-dataset.yaml \  epochs=100 imgsz=640 batch=16
Von Grund auf
from libreyolo import LibreYOLONAS # Es wird kein Deci-Checkpoint verwendet: Das Modell startet mit zufälligen Gewichten,# sodass das Ergebnis des Laufs ausschließlich aus deinen Daten hervorgeht.model = LibreYOLONAS(None, size="s")model.train(data="my-dataset.yaml", imgsz=640, batch=16)

Wenn du epochs, lr0 und amp auslässt, werden sie aufgabenspezifisch bestimmt. Ein Lauf zur Posenschätzung beginnt daher mit anderen Standardwerten als ein Erkennungslauf. Als Optimierer wird standardmäßig AdamW verwendet. Die Klassenanzahl stammt aus der Datensatz-YAML-Datei und der Kopf wird vor der ersten Epoche entsprechend neu aufgebaut. Beim Pose-Kopf wird die Keypoint-Anzahl auf dieselbe Weise behandelt, sodass sich ein COCO-Pose-Checkpoint auf ein Skelett anderer Größe feinabstimmen lässt.

Das Fine-Tuning beginnt mit Decis Gewichten, die Decis Lizenz unterliegen. Beim Training eines zufällig initialisierten Modells wird dagegen keinerlei Deci-Checkpoint verwendet. Dies zeigt das dritte Snippet oben.

Unter Training findest du Informationen zu Datensätzen, Augmentation, Multi-GPU und Loggern.

Die Erkennung verwendet standardmäßig amp=True mit amp_dtype="float16"; das Training orientierter Boxen behält amp=False bei. Der OBB-Head unterstützt Training, Vorhersage und Validierung, verwendet Spiegelungs-/HSV-Augmentierung und wählt Checkpoints anhand von metrics/mAP50-95(OBB). load_detect_weights_for_obb() initialisiert ihn mit Erkennungsgewichten.

Validierung

val() gibt ein Dictionary mit metrics/-Schlüsseln für Precision, Recall, mAP 50 und mAP 50-95 zurück, gemessen anhand jedes Datensatzes im Format, das du für das Training verwendet hast.

Python
from libreyolo import LibreYOLO model = LibreYOLO("LibreYOLONASs.pt")metrics = model.val(data="my-dataset.yaml") print(metrics["metrics/mAP50-95"])print(metrics["metrics/mAP50"])
CLI
libreyolo val model=LibreYOLONASs.pt data=my-dataset.yaml
Gegen COCO
# Die mitgelieferte COCO-YAML-Datei enthält ein Downloadskript und benötigt# daher eine ausdrückliche Berechtigung, sofern der Datensatz noch nicht lokal vorliegt.libreyolo val model=LibreYOLONASl.pt data=coco.yaml imgsz=640 \  allow_download_scripts=True

Export

AufgabeONNXTorchScriptExecuTorchTensorRTOpenVINOPaddleMNNRKNNncnnTFLiteCoreMLCore AI
DetectionDetection to ONNX: unterstütztDetection to TorchScript: unterstütztDetection to ExecuTorch: unterstütztDetection to TensorRT: unterstütztDetection to OpenVINO: unterstütztDetection to Paddle: unterstütztDetection to MNN: unterstütztDetection to RKNN: unterstütztDetection to ncnn: unterstütztDetection to TFLite: unterstütztDetection to CoreML: nicht unterstütztDetection to Core AI: unterstützt
PosePose to ONNX: unterstütztPose to TorchScript: unterstütztPose to ExecuTorch: unterstütztPose to TensorRT: unterstütztPose to OpenVINO: unterstütztPose to Paddle: unterstütztPose to MNN: nicht unterstütztPose to RKNN: nicht unterstütztPose to ncnn: unterstütztPose to TFLite: nicht unterstütztPose to CoreML: nicht unterstütztPose to Core AI: nicht unterstützt
Oriented boxesOriented boxes to ONNX: unterstütztOriented boxes to TorchScript: unterstütztOriented boxes to ExecuTorch: unterstütztOriented boxes to TensorRT: unterstütztOriented boxes to OpenVINO: unterstütztOriented boxes to Paddle: nicht unterstütztOriented boxes to MNN: nicht unterstütztOriented boxes to RKNN: nicht unterstütztOriented boxes to ncnn: unterstütztOriented boxes to TFLite: nicht unterstütztOriented boxes to CoreML: nicht unterstütztOriented boxes to Core AI: nicht unterstützt

Ein exportiertes Artefakt wird über seine Dateiendung wieder durch LibreYOLO() geladen. Eine .onnx- oder .engine-Datei verhält sich daher wie ein Checkpoint und gibt dasselbe Results-Objekt zurück. Du kannst den Graphen auch in einer eigenständigen Laufzeitumgebung ohne installiertes LibreYOLO ausführen. Dann musst du Vor- und Nachverarbeitung selbst implementieren. Jedes Format installiert ein anderes Extra und besitzt eigene Argumente. Beides ist auf der Seite des jeweiligen Formats beschrieben.

Ein Export ist eine weitere Kopie derselben Gewichte in einem anderen Container. Der Export eines Deci-Checkpoints ändert weder die Herkunft der Gewichte noch die dafür geltende Lizenz.

Python
from libreyolo import LibreYOLO model = LibreYOLO("LibreYOLONASs.pt")model.export(format="onnx", imgsz=640)
CLI
libreyolo export model=LibreYOLONASs.pt format=onnx imgsz=640
Exportierte Datei verwenden
from libreyolo import LibreYOLO, SAMPLE_IMAGE # Die Factory leitet anhand der Dateiendung weiter, daher wird ein exportiertes Artefakt# wie jeder Checkpoint geladen und gibt dasselbe Results-Objekt zurück.model = LibreYOLO("LibreYOLONASs.onnx")result = model(SAMPLE_IMAGE) print(result.boxes.xyxy)

ONNX-Ein- und Ausgaben

LibreYOLONAS detect

Tensorimages float32 [batch, 3, height, width]
FarbeRGB
SkalierungPixel / 255
Normalisierungkeine
Größenanpassungcustom, Pillow bilinear
So reproduzierst du die bilineare Skalierung von Pillow

LibreYOLO skaliert mit dem BILINEAR-Filter von Pillow (Image.resize). Das ist weder OpenCV INTER_LINEAR noch INTER_AREA: Beim Verkleinern weitet Pillow den Filter um den Verkleinerungsfaktor, und die Skalierungen von OpenCV verändern Detektionen und verschieben Boxen um mehrere Pixel. Um es ohne Pillow nachzubauen, skaliere eine Achse, runde auf 8 Bit, skaliere dann die andere Achse und runde erneut. Pro Achse gilt s = in_size / out_size und f = max(s, 1). Ausgabepixel i hat das Zentrum c = (i + 0.5) * s und liest Quellpixel j von int(c - f + 0.5) bis int(c + f + 0.5) - 1, auf das Bild begrenzt, jeweils mit dem Gewicht max(0, 1 - |j + 0.5 - c| / f), geteilt durch die Summe der Gewichte. Pillow rechnet in Festkomma und wählt die Achsenreihenfolge anhand der Bildform, daher können Gleitkomma-Gewichte bei einigen Pixeln um eine Stufe abweichen. Das ändert die Ergebnisse in unseren Prüfungen nicht.

Square input only. Export rejects a non-square imgsz, and height equals width, 640 by default.

The image is not scaled to fill the canvas. The longest side goes to R = min(636, height, width), so 636 at 640 x 640.

Scale by r = min(R / h, R / w) and resize to (round(w * r), round(h * r)). The rounding is Python round, so an exact .5 goes to the even neighbor.

Paste the resized image onto a canvas filled with 114 at left = (width - new_w) // 2 and top = (height - new_h) // 2.

On the test image, cv2.resize with INTER_LINEAR loses two of the eight detections, and INTER_AREA moves boxes by up to 1.4 px.

Divide by 255 after the resize. There is no mean or std normalization.

Detection, Standardexport
AusgabeFormBedeutung
pred_logits[batch, anchors, 4]Boxes, despite the name. x1, y1, x2, y2 in input-canvas pixels. anchors is the cell count over strides 8, 16 and 32, 8400 at 640 x 640.
pred_boxes[batch, anchors, nc]Class scores, despite the name. Sigmoid already applied. 80 classes for the COCO checkpoints.

Nachbearbeitung

  1. The output names are swapped relative to their content. Read boxes from pred_logits and scores from pred_boxes, or tell them apart by the last dimension (4 for boxes).
  2. Take the best class per anchor: score = max over classes, class = argmax. One anchor yields at most one detection.
  3. Keep anchors whose score is strictly above the confidence threshold (0.25 by default).
  4. Keep the 1000 highest scoring candidates.
  5. Map boxes back to the original image: subtract left from x and top from y, divide by r, clip to the image. Drop boxes left with zero width or height.
  6. Run NMS per class with IoU 0.45 and keep at most 300 detections.
  7. nms=True is not available for this family: export raises NotImplementedError.

LibreYOLONAS pose

Tensorimages float32 [batch, 3, height, width]
FarbeBGR
SkalierungPixel / 255
Normalisierungkeine
Größenanpassungcustom, Pillow bilinear
So reproduzierst du die bilineare Skalierung von Pillow

LibreYOLO skaliert mit dem BILINEAR-Filter von Pillow (Image.resize). Das ist weder OpenCV INTER_LINEAR noch INTER_AREA: Beim Verkleinern weitet Pillow den Filter um den Verkleinerungsfaktor, und die Skalierungen von OpenCV verändern Detektionen und verschieben Boxen um mehrere Pixel. Um es ohne Pillow nachzubauen, skaliere eine Achse, runde auf 8 Bit, skaliere dann die andere Achse und runde erneut. Pro Achse gilt s = in_size / out_size und f = max(s, 1). Ausgabepixel i hat das Zentrum c = (i + 0.5) * s und liest Quellpixel j von int(c - f + 0.5) bis int(c + f + 0.5) - 1, auf das Bild begrenzt, jeweils mit dem Gewicht max(0, 1 - |j + 0.5 - c| / f), geteilt durch die Summe der Gewichte. Pillow rechnet in Festkomma und wählt die Achsenreihenfolge anhand der Bildform, daher können Gleitkomma-Gewichte bei einigen Pixeln um eine Stufe abweichen. Das ändert die Ergebnisse in unseren Prüfungen nicht.

Square input only. Export rejects a non-square imgsz, and height equals width, 640 by default.

Channels are BGR, unlike detection. Pad value and position also differ from detection.

The longest side goes to R = min(640, height, width), so it fills the canvas.

Scale by r = min(R / h, R / w) and resize to (round(w * r), round(h * r)). The rounding is Python round, so an exact .5 goes to the even neighbor.

Paste the resized image in the top-left corner of a canvas filled with 127. All padding is on the bottom and the right.

On the test image, cv2.resize with INTER_LINEAR or INTER_AREA moves boxes by up to 5 px and keypoints by more than 10 px.

Divide by 255 after the resize. There is no mean or std normalization.

Pose, Standardexport
AusgabeFormBedeutung
boxes[batch, anchors, 4]Person boxes as x1, y1, x2, y2 in input-canvas pixels. anchors is the cell count over strides 8, 16 and 32, 8400 at 640 x 640.
scores[batch, anchors, nc]Class scores, sigmoid already applied. nc is 1 (person) for the COCO pose checkpoints.
keypoints_xy[batch, anchors, num_keypoints, 2]Keypoint x, y in input-canvas pixels. num_keypoints is 17 (COCO order) for the COCO pose checkpoints.
keypoints_conf[batch, anchors, num_keypoints]Per-keypoint visibility score, sigmoid already applied.

Nachbearbeitung

  1. Take the best class per anchor: score = max over classes, class = argmax. With one class this is just the person score.
  2. Keep anchors whose score is at or above the confidence threshold (0.25 by default). This is >=, not > as in detection.
  3. Keep the 1000 highest scoring candidates.
  4. Map boxes and keypoints back to the original image: divide x and y by r. The image sits in the top-left corner, so there is no pad offset to subtract.
  5. Clip boxes to the image and drop boxes left with zero width or height. Keypoints are not clipped and can fall outside the image.
  6. Run NMS per class with IoU 0.45 and keep at most 300 detections. Keep each survivor's keypoints as (x, y, keypoints_conf).
  7. nms=True is not available for this family: export raises NotImplementedError.

LibreYOLONAS obb

Tensorimages float32 [batch, 3, height, width]
FarbeBGR
SkalierungPixel / 255
Normalisierungkeine
Größenanpassungcustom, bilinear

Square input only. Export rejects a non-square imgsz, and height equals width, 1024 by default.

Channels are BGR, unlike detection. The resize filter and the pad position also differ from detection.

The longest side goes to R = min(1024, height, width), so it fills the canvas.

Scale by r = min(R / h, R / w) and resize to (round(w * r), round(h * r)). The rounding is Python round, so an exact .5 goes to the even neighbor.

The resize is cv2.resize with INTER_LINEAR, not Pillow as in detection and pose. It is skipped when the image already has that size. On the test image, Pillow's filter here changes the detection count.

Paste the resized image in the top-left corner of a canvas filled with 114. All padding is on the bottom and the right.

Divide by 255 after the resize. There is no mean or std normalization.

Oriented boxes, Standardexport
AusgabeFormBedeutung
boxes[batch, anchors, 5]Rotated boxes as cx, cy, w, h, angle. cx, cy, w and h are in input-canvas pixels. The angle is in radians. The graph computes it as (sigmoid(logit) - 0.25) x pi, so it lies between -pi/4 and 3pi/4 and is not wrapped yet. The w side points along (cos angle, sin angle) in image coordinates, y down. anchors is the cell count over strides 8, 16 and 32, 21504 at 1024 x 1024.
scores[batch, anchors, nc]Class scores, sigmoid already applied. 18 classes (DOTA 2.0) for the published checkpoints.

Nachbearbeitung

  1. Take the best class per anchor: score = max over classes, class = argmax. One anchor yields at most one detection.
  2. Keep anchors whose score is at or above the confidence threshold (0.25 by default). This is >=, not > as in detection.
  3. Keep the 1000 highest scoring candidates.
  4. Map boxes back to the original image: divide cx, cy, w and h by r. The image sits in the top-left corner, so there is no pad offset, and the angle does not change.
  5. Clip cx to 0 to the image width and cy to 0 to the image height. w and h are not clipped. Drop boxes with w or h at or below 0.
  6. Put the long side first: if h > w, swap w and h and add pi/2 to the angle. Then wrap the angle to [-pi/2, pi/2) with angle = ((angle + pi/2) mod pi) - pi/2.
  7. Run greedy NMS per class on exact rotated-box IoU (polygon intersection area over union, for example cv2.rotatedRectangleIntersection) with IoU 0.45, and keep at most 300 detections. LibreYOLO does not use upstream's matrix soft-NMS.
  8. LibreYOLO also reports an axis-aligned box per detection. With ex = abs(cos angle) * w / 2 + abs(sin angle) * h / 2 and ey = abs(sin angle) * w / 2 + abs(cos angle) * h / 2, it is cx - ex, cy - ey, cx + ex, cy + ey, clipped to the image.
  9. nms=True is not available for this family: export raises NotImplementedError.

Um deine eigene Implementierung zu prüfen, lade dieselbe Datei mit LibreYOLO: LibreYOLO("model.onnx").predict("image.jpg") liefert die Referenzergebnisse. Geprüft mit LibreYOLO 1.7.0.

Checkpoints

Es gibt keine aufzulisten. Decis Lizenz verbietet die Weiterverteilung, daher veröffentlicht die LibreYOLO-Organisation keine YOLO-NAS-Gewichte und der Download wird an anderer Stelle aufgelöst. Ein Name der Form LibreYOLONAS<size>.pt, für die Posenschätzung LibreYOLONAS<size>-pose.pt oder für orientierte Boxen LibreYOLONAS<size>-obb.pt (s, m, l) wird dem passenden Objekt auf Decis öffentlichem CDN zugeordnet.

Auf diese Weise lassen sich nur Checkpoints abrufen, deren SHA-256 die Bibliothek fest hinterlegt hat. Alle anderen werden sicher abgelehnt, statt ein ungeprüftes Pickle eines Drittanbieters zu öffnen. Du musst sie manuell herunterladen und als Pfad übergeben. Eine bereits lokal vorhandene Datei wird ohne Download und Prüfsummenprüfung von ihrem Pfad geladen. Das gilt auch für eine Deci-Datei mit der ursprünglichen Endung .pth, die der Loader erkennt.

Lizenzierung

Prüfe die Lizenz im Hugging-Face-Repository der konkreten Gewichte, die du herunterlädst. Jeder Checkpoint in der LibreYOLO-Organisation hat eine Lizenz, und sie ist innerhalb einer Familie nicht immer gleich. Dieses Repository ist die maßgebliche Quelle. Die Zusammenfassung unten beschreibt den Stand bei der letzten Verifizierung dieser Seite.

Dies ist eine Beschreibung der beteiligten Lizenzen und keine Rechtsberatung. Wenn die Antwort kommerziell relevant ist, lies die Lizenzen selbst und hole eigenen Rechtsrat ein.

Originalarbeit
YOLO-NAS, Deci.AI
Upstream-Lizenz
Deci.AI proprietary, non-commercial
LibreYOLO-Code
MIT
Gewichte
Deci.AI proprietary, non-commercial, von den Autoren verbreitet. LibreYOLO hostet oder spiegelt sie nicht.
Einordnung
Two licenses apply here and they are not the same. The SuperGradients source this port follows is Apache-2.0 and LibreYOLO's own implementation is MIT, so nothing restricts the architecture or the training code. Deci's published checkpoints are a different matter: the YOLO-NAS license grants a revocable, non-transferable right to use them and nothing more. It forbids redistribution and sublicensing, forbids offering them as a managed or remote service, restricts modification and reverse engineering, and rules out commercial use, including any model running in a production environment, unless you hold a separate agreement with Deci. LibreYOLO therefore does not mirror them, and prints those terms once before the download starts. Weights trained from a randomly initialized model on your own data derive from no Deci checkpoint.

LibreYOLO hostet oder spiegelt diese Gewichte nicht. In der LibreYOLO-Organisation auf Hugging Face gibt es nichts für diese Familie. Jeder automatische Download verwendet stattdessen Decis öffentliches CDN, zeigt vor dem Start einmal pro Prozess Decis Bedingungen an und wird vor dem Öffnen anhand einer fest hinterlegten SHA-256 geprüft.

Eine Alternative ist das Training mit einem zufällig initialisierten Modell. Die Architektur steht im Upstream-Projekt unter Apache-2.0 und hier unter MIT. Ein auf diese Weise mit deinen eigenen Daten trainiertes Modell leitet sich daher von keinem Deci-Checkpoint ab.

Zitieren

YOLO-NAS wurde ohne Paper veröffentlicht. Der folgende Eintrag entspricht der von den Autoren gewünschten Angabe und bezieht sich auf SuperGradients, die Bibliothek, mit der es veröffentlicht wurde.

@misc{supergradients,
  doi = {10.5281/ZENODO.7789328},
  url = {https://zenodo.org/record/7789328},
  author = {Aharon,  Shay and {Louis-Dupont} and {Ofri Masad} and Yurkova,  Kate and {Lotem Fridman} and {Lkdci} and Khvedchenya,  Eugene and Rubin,  Ran and Bagrov,  Natan and Tymchenko,  Borys and Keren,  Tomer and Zhilko,  Alexander and {Eran-Deci}},
  title = {Super-Gradients},
  publisher = {GitHub},
  journal = {GitHub repository},
  year = {2021},
}

Aus dem Zitierblock der Autoren unter github.com/Deci-AI/super-gradients#citing kopiert.

Mit LibreYOLO v1.6.0 verifiziert. Supporttabellen, Checkpoints und Benchmarkwerte auf dieser Seite werden aus der veröffentlichten Bibliothek und den publizierten Gewichten generiert und nicht von Hand geschrieben.