Meet YOLO26: next-gen vision AI.

Link to this sectionUtility semplici#

YOLO model code with 3D perspective visualization

Il pacchetto ultralytics fornisce una varietà di utility per supportare, migliorare e accelerare i tuoi flussi di lavoro. Sebbene ce ne siano molte altre disponibili, questa guida mette in evidenza alcune delle più utili per gli sviluppatori, fungendo da riferimento pratico per la programmazione con gli strumenti Ultralytics.



Watch: Ultralytics Utilities | Auto Annotation, Explorer API and Dataset Conversion

Link to this sectionDati#

Link to this sectionAuto-etichettatura / Annotazioni#

L'annotazione del dataset è un processo che richiede molte risorse e tempo. Se hai un modello di object detection Ultralytics YOLO addestrato su una quantità ragionevole di dati, puoi usarlo con SAM per auto-annotare ulteriori dati in formato di segmentazione.

from ultralytics.data.annotator import auto_annotate

auto_annotate(
    data="path/to/new/data",
    det_model="yolo26n.pt",
    sam_model="mobile_sam.pt",
    device="cuda",
    output_dir="path/to/save_labels",
)

Questa funzione non restituisce alcun valore. Per ulteriori dettagli:

Link to this sectionVisualizza le annotazioni del dataset#

Questa funzione visualizza le annotazioni YOLO su un'immagine prima dell'addestramento, aiutando a identificare e correggere eventuali annotazioni errate che potrebbero portare a risultati di rilevamento sbagliati. Disegna bounding box, etichetta gli oggetti con i nomi delle classi e regola il colore del testo in base alla luminanza dello sfondo per una migliore leggibilità.

from ultralytics.data.utils import visualize_image_annotations

label_map = {  # Define the label map with all annotated class labels.
    0: "person",
    1: "car",
}

# Visualize
visualize_image_annotations(
    "path/to/image.jpg",  # Input image path.
    "path/to/annotations.txt",  # Annotation file path for the image.
    label_map,
)

Link to this sectionConverti maschere di segmentazione in formato YOLO#

Maschere di segmentazione in formato YOLO

Usa questo strumento per convertire un dataset di immagini con maschere di segmentazione nel formato di segmentazione Ultralytics YOLO. Questa funzione prende la directory contenente le immagini della maschera in formato binario e le converte nel formato di segmentazione YOLO.

Le maschere convertite verranno salvate nella directory di output specificata.

from ultralytics.data.converter import convert_segment_masks_to_yolo_seg

# The classes here is the total classes in the dataset.
# for COCO dataset we have 80 classes.
convert_segment_masks_to_yolo_seg(masks_dir="path/to/masks_dir", output_dir="path/to/output_dir", classes=80)

Link to this sectionConverti COCO in formato YOLO#

Usa questo strumento per convertire le annotazioni JSON di COCO nel formato YOLO. Per dataset di object detection (bounding box), imposta use_segments e use_keypoints su False.

from ultralytics.data.converter import convert_coco

convert_coco(
    "coco/annotations/",
    use_segments=False,
    use_keypoints=False,
    cls91to80=True,
)

Per ulteriori informazioni sulla funzione convert_coco, visita la pagina di riferimento.

Link to this sectionOttieni dimensioni dei bounding box#

import cv2

from ultralytics import YOLO
from ultralytics.utils.plotting import Annotator

model = YOLO("yolo26n.pt")  # Load pretrain or fine-tune model

# Process the image
source = cv2.imread("path/to/image.jpg")
results = model(source)

# Extract results
annotator = Annotator(source, example=model.names)

for box in results[0].boxes.xyxy.cpu():
    width, height, area = annotator.get_bbox_dimension(box)
    print(f"Bounding Box Width {width.item()}, Height {height.item()}, Area {area.item()}")

Link to this sectionConverti bounding box in segmenti#

Con dati di bounding box x y w h esistenti, converti in segmenti usando la funzione yolo_bbox2segment. Organizza i file per immagini e annotazioni come segue:

data
|__ images
    ├─ 001.jpg
    ├─ 002.jpg
    ├─ ..
    └─ NNN.jpg
|__ labels
    ├─ 001.txt
    ├─ 002.txt
    ├─ ..
    └─ NNN.txt
from ultralytics.data.converter import yolo_bbox2segment

yolo_bbox2segment(
    im_dir="path/to/images",
    save_dir=None,  # saved to "labels-segment" in images directory
    sam_model="sam_b.pt",
)

Visita la pagina di riferimento di yolo_bbox2segment per maggiori informazioni sulla funzione.

Link to this sectionConverti segmenti in bounding box#

Se hai un dataset che usa il formato dataset di segmentazione, puoi convertirlo facilmente in bounding box verticali (o orizzontali) (formato x y w h) con questa funzione.

import numpy as np

from ultralytics.utils.ops import segments2boxes

segments = np.array(
    [
        [805, 392, 797, 400, ..., 808, 714, 808, 392],
        [115, 398, 113, 400, ..., 150, 400, 149, 298],
        [267, 412, 265, 413, ..., 300, 413, 299, 412],
    ]
)

segments2boxes([s.reshape(-1, 2) for s in segments])
# >>> array([[ 741.66, 631.12, 133.31, 479.25],
#           [ 146.81, 649.69, 185.62, 502.88],
#           [ 281.81, 636.19, 118.12, 448.88]],
#           dtype=float32) # xywh bounding boxes

Per capire come funziona questa funzione, visita la pagina di riferimento.

Link to this sectionUtility#

Link to this sectionCompressione immagini#

Comprimi un singolo file immagine a una dimensione ridotta preservandone le proporzioni e la qualità. Se l'immagine di input è più piccola della dimensione massima, non verrà ridimensionata.

from pathlib import Path

from ultralytics.data.utils import compress_one_image

for f in Path("path/to/dataset").rglob("*.jpg"):
    compress_one_image(f)

Link to this sectionAuto-split del dataset#

Suddividi automaticamente un dataset in split di train/val/test e salva gli split risultanti in file autosplit_*.txt. Questa funzione usa il campionamento casuale, che viene escluso quando si usa l'argomento fraction per l'addestramento.

from ultralytics.data.split import autosplit

autosplit(
    path="path/to/images",
    weights=(0.9, 0.1, 0.0),  # (train, validation, test) fractional splits
    annotated_only=False,  # split only images with annotation file when True
)

Vedi la pagina di riferimento per ulteriori dettagli su questa funzione.

Link to this sectionSegmento-poligono a maschera binaria#

Converti un singolo poligono (come lista) in una maschera binaria della dimensione immagine specificata. Il poligono deve essere un array 1D piatto di N coordinate che elencano valori x, y alternati che definiscono il contorno del poligono.

Avviso

N deve essere sempre pari.

import numpy as np

from ultralytics.data.utils import polygon2mask

imgsz = (1080, 810)
polygon = np.array([805, 392, 797, 400, ..., 808, 714, 808, 392])  # (238, 2)

mask = polygon2mask(
    imgsz,  # tuple
    [polygon],  # input as list
    color=255,  # 8-bit binary
    downsample_ratio=1,
)

Link to this sectionBounding box#

Link to this sectionIstanze di bounding box (orizzontali)#

Per gestire i dati dei bounding box, la classe Bboxes aiuta a convertire tra formati di coordinate box, scalare le dimensioni dei box, calcolare aree, includere offset e altro.

import numpy as np

from ultralytics.utils.instance import Bboxes

boxes = Bboxes(
    bboxes=np.array(
        [
            [22.878, 231.27, 804.98, 756.83],
            [48.552, 398.56, 245.35, 902.71],
            [669.47, 392.19, 809.72, 877.04],
            [221.52, 405.8, 344.98, 857.54],
            [0, 550.53, 63.01, 873.44],
            [0.0584, 254.46, 32.561, 324.87],
        ]
    ),
    format="xyxy",
)

boxes.areas()
# >>> array([ 4.1104e+05,       99216,       68000,       55772,       20347,      2288.5])

boxes.convert("xywh")
print(boxes.bboxes)
# >>> array(
#     [[ 413.93, 494.05,  782.1, 525.56],
#      [ 146.95, 650.63,  196.8, 504.15],
#      [  739.6, 634.62, 140.25, 484.85],
#      [ 283.25, 631.67, 123.46, 451.74],
#      [ 31.505, 711.99,  63.01, 322.91],
#      [  16.31, 289.67, 32.503,  70.41]]
# )

Vedi la sezione di riferimento di Bboxes per ulteriori attributi e metodi.

Suggerimento

Molte delle seguenti funzioni (e altre) possono essere accessibili usando la classe Bboxes, ma se preferisci lavorare direttamente con le funzioni, vedi le prossime sottosezioni su come importarle indipendentemente.

Link to this sectionScalatura dei box#

Quando ingrandisci o riduci un'immagine, puoi scalare in modo appropriato le coordinate dei bounding box corrispondenti per farle coincidere usando ultralytics.utils.ops.scale_boxes.

import cv2 as cv
import numpy as np

from ultralytics.utils.ops import scale_boxes

image = cv.imread("ultralytics/assets/bus.jpg")
h, w, c = image.shape
resized = cv.resize(image, None, (), fx=1.2, fy=1.2)
new_h, new_w, _ = resized.shape

xyxy_boxes = np.array(
    [
        [22.878, 231.27, 804.98, 756.83],
        [48.552, 398.56, 245.35, 902.71],
        [669.47, 392.19, 809.72, 877.04],
        [221.52, 405.8, 344.98, 857.54],
        [0, 550.53, 63.01, 873.44],
        [0.0584, 254.46, 32.561, 324.87],
    ]
)

new_boxes = scale_boxes(
    img1_shape=(h, w),  # original image dimensions
    boxes=xyxy_boxes,  # boxes from original image
    img0_shape=(new_h, new_w),  # resized image dimensions (scale to)
    ratio_pad=None,
    padding=False,
    xywh=False,
)

print(new_boxes)
# >>> array(
#     [[  27.454,  277.52,  965.98,   908.2],
#     [   58.262,  478.27,  294.42,  1083.3],
#     [   803.36,  470.63,  971.66,  1052.4],
#     [   265.82,  486.96,  413.98,    1029],
#     [        0,  660.64,  75.612,  1048.1],
#     [   0.0701,  305.35,  39.073,  389.84]]
# )

Link to this sectionConversioni di formato dei bounding box#

Link to this sectionXYXY → XYWH#

Converti le coordinate dei bounding box dal formato (x1, y1, x2, y2) al formato (x, y, larghezza, altezza), dove (x1, y1) è l'angolo in alto a sinistra e (x2, y2) è l'angolo in basso a destra.

import numpy as np

from ultralytics.utils.ops import xyxy2xywh

xyxy_boxes = np.array(
    [
        [22.878, 231.27, 804.98, 756.83],
        [48.552, 398.56, 245.35, 902.71],
        [669.47, 392.19, 809.72, 877.04],
        [221.52, 405.8, 344.98, 857.54],
        [0, 550.53, 63.01, 873.44],
        [0.0584, 254.46, 32.561, 324.87],
    ]
)
xywh = xyxy2xywh(xyxy_boxes)

print(xywh)
# >>> array(
#     [[ 413.93,  494.05,   782.1, 525.56],
#     [  146.95,  650.63,   196.8, 504.15],
#     [   739.6,  634.62,  140.25, 484.85],
#     [  283.25,  631.67,  123.46, 451.74],
#     [  31.505,  711.99,   63.01, 322.91],
#     [   16.31,  289.67,  32.503,  70.41]]
# )

Link to this sectionTutte le conversioni di bounding box#

from ultralytics.utils.ops import (
    ltwh2xywh,
    ltwh2xyxy,
    xywh2ltwh,  # xywh → top-left corner, w, h
    xywh2xyxy,
    xywhn2xyxy,  # normalized → pixel
    xyxy2ltwh,  # xyxy → top-left corner, w, h
    xyxy2xywhn,  # pixel → normalized
)

for func in (ltwh2xywh, ltwh2xyxy, xywh2ltwh, xywh2xyxy, xywhn2xyxy, xyxy2ltwh, xyxy2xywhn):
    print(help(func))  # print function docstrings

See the docstring for each function or visit the ultralytics.utils.ops reference page to read more.

Link to this sectionPlotting#

Link to this sectionUtility di annotazione#

Ultralytics include una classe Annotator per annotare vari tipi di dati. È meglio utilizzarla con bounding box di object detection, keypoint di posa e bounding box orientati.

Link to this sectionAnnotazione box#

Esempi Python usando Ultralytics YOLO 🚀
import cv2 as cv
import numpy as np

from ultralytics.utils.plotting import Annotator, colors

names = {
    0: "person",
    5: "bus",
    11: "stop sign",
}

image = cv.imread("ultralytics/assets/bus.jpg")
ann = Annotator(
    image,
    line_width=None,  # default auto-size
    font_size=None,  # default auto-size
    font="Arial.ttf",  # must be ImageFont compatible
    pil=False,  # use PIL, otherwise uses OpenCV
)

xyxy_boxes = np.array(
    [
        [5, 22.878, 231.27, 804.98, 756.83],  # class-idx x1 y1 x2 y2
        [0, 48.552, 398.56, 245.35, 902.71],
        [0, 669.47, 392.19, 809.72, 877.04],
        [0, 221.52, 405.8, 344.98, 857.54],
        [0, 0, 550.53, 63.01, 873.44],
        [11, 0.0584, 254.46, 32.561, 324.87],
    ]
)

for nb, box in enumerate(xyxy_boxes):
    c_idx, *box = box
    label = f"{str(nb).zfill(2)}:{names.get(int(c_idx))}"
    ann.box_label(box, label, color=colors(c_idx, bgr=True))

image_with_bboxes = ann.result()

I nomi possono essere usati da model.names quando lavori con i risultati di rilevamento. Vedi anche la pagina di riferimento di Annotator per ulteriori approfondimenti.

Link to this sectionAnnotazione sweep di Ultralytics#

Annotazione sweep usando le utility Ultralytics
import cv2
import numpy as np

from ultralytics import YOLO
from ultralytics.solutions.solutions import SolutionAnnotator
from ultralytics.utils.plotting import colors

# User defined video path and model file
cap = cv2.VideoCapture("path/to/video.mp4")
model = YOLO(model="yolo26s-seg.pt")  # Model file, e.g., yolo26s.pt or yolo26m-seg.pt

if not cap.isOpened():
    print("Error: Could not open video.")
    exit()

# Initialize the video writer object.
w, h, fps = (int(cap.get(x)) for x in (cv2.CAP_PROP_FRAME_WIDTH, cv2.CAP_PROP_FRAME_HEIGHT, cv2.CAP_PROP_FPS))
video_writer = cv2.VideoWriter("ultralytics.avi", cv2.VideoWriter_fourcc(*"mp4v"), fps, (w, h))

masks = None  # Initialize variable to store masks data
f = 0  # Initialize frame count variable for enabling mouse event.
line_x = w  # Store width of line.
dragging = False  # Initialize bool variable for line dragging.
classes = model.names  # Store model classes names for plotting.
window_name = "Ultralytics Sweep Annotator"

def drag_line(event, x, _, flags, param):
    """Mouse callback function to enable dragging a vertical sweep line across the video frame."""
    global line_x, dragging
    if event == cv2.EVENT_LBUTTONDOWN or (flags & cv2.EVENT_FLAG_LBUTTON):
        line_x = max(0, min(x, w))
        dragging = True

while cap.isOpened():  # Loop over the video capture object.
    ret, im0 = cap.read()
    if not ret:
        break
    f = f + 1  # Increment frame count.
    count = 0  # Re-initialize count variable on every frame for precise counts.
    results = model.track(im0, persist=True)[0]

    if f == 1:
        cv2.namedWindow(window_name)
        cv2.setMouseCallback(window_name, drag_line)

    annotator = SolutionAnnotator(im0)

    if results.boxes.is_track:
        if results.masks is not None:
            masks = [np.array(m, dtype=np.int32) for m in results.masks.xy]

        boxes = results.boxes.xyxy.tolist()
        track_ids = results.boxes.id.int().cpu().tolist()
        clss = results.boxes.cls.cpu().tolist()

        for mask, box, cls, t_id in zip(masks or [None] * len(boxes), boxes, clss, track_ids):
            color = colors(t_id, True)  # Assign different color to each tracked object.
            label = f"{classes[cls]}:{t_id}"
            if mask is not None and mask.size > 0:
                if box[0] > line_x:
                    count += 1
                    cv2.polylines(im0, [mask], True, color, 2)
                    x, y = mask.min(axis=0)
                    (w_m, _), _ = cv2.getTextSize(label, cv2.FONT_HERSHEY_SIMPLEX, 0.5, 1)
                    cv2.rectangle(im0, (x, y - 20), (x + w_m, y), color, -1)
                    cv2.putText(im0, label, (x, y - 5), cv2.FONT_HERSHEY_SIMPLEX, 0.5, (255, 255, 255), 1)
            else:
                if box[0] > line_x:
                    count += 1
                    annotator.box_label(box=box, color=color, label=label)

    # Generate draggable sweep line
    annotator.sweep_annotator(line_x=line_x, line_y=h, label=f"COUNT:{count}")

    cv2.imshow(window_name, im0)
    video_writer.write(im0)
    if cv2.waitKey(1) & 0xFF == ord("q"):
        break

# Release the resources
cap.release()
video_writer.release()
cv2.destroyAllWindows()

Trova ulteriori dettagli sul metodo sweep_annotator nella nostra sezione di riferimento qui.

Link to this sectionAnnotazione adaptive label#

Avviso

A partire da Ultralytics v8.3.167, circle_label e text_label sono stati sostituiti da una funzione unificata adaptive_label. Ora puoi specificare il tipo di annotazione usando l'argomento shape:

  • Rettangolo: annotator.adaptive_label(box, label=names[int(cls)], color=colors(cls, True), shape="rect")
  • Cerchio: annotator.adaptive_label(box, label=names[int(cls)], color=colors(cls, True), shape="circle")


Watch: In-Depth Guide to Text & Circle Annotations with Python Live Demos | Ultralytics Annotations 🚀
Annotazione adaptive label usando le utility Ultralytics
import cv2

from ultralytics import YOLO
from ultralytics.solutions.solutions import SolutionAnnotator
from ultralytics.utils.plotting import colors

model = YOLO("yolo26s.pt")
names = model.names
cap = cv2.VideoCapture("path/to/video.mp4")

w, h, fps = (int(cap.get(x)) for x in (cv2.CAP_PROP_FRAME_WIDTH, cv2.CAP_PROP_FRAME_HEIGHT, cv2.CAP_PROP_FPS))
writer = cv2.VideoWriter("Ultralytics circle annotation.avi", cv2.VideoWriter_fourcc(*"MJPG"), fps, (w, h))

while True:
    ret, im0 = cap.read()
    if not ret:
        break

    annotator = SolutionAnnotator(im0)
    results = model.predict(im0)[0]
    boxes = results.boxes.xyxy.cpu()
    clss = results.boxes.cls.cpu().tolist()

    for box, cls in zip(boxes, clss):
        annotator.adaptive_label(box, label=names[int(cls)], color=colors(cls, True), shape="circle")
    writer.write(im0)
    cv2.imshow("Ultralytics circle annotation", im0)

    if cv2.waitKey(1) & 0xFF == ord("q"):
        break

writer.release()
cap.release()
cv2.destroyAllWindows()

Vedi la pagina di riferimento di SolutionAnnotator per ulteriori approfondimenti.

Link to this sectionVarie#

Link to this sectionProfiling del codice#

Controlla la durata di esecuzione/elaborazione del codice usando with o come decoratore.

from ultralytics.utils.ops import Profile

with Profile(device="cuda:0") as dt:
    pass  # operation to measure

print(dt)
# >>> "Elapsed time is 9.5367431640625e-07 s"

Link to this sectionFormati supportati da Ultralytics#

Hai bisogno di usare programmaticamente i formati immagine o video supportati in Ultralytics? Usa queste costanti se necessario:

from ultralytics.data.utils import IMG_FORMATS, VID_FORMATS

print(IMG_FORMATS)
# {'avif', 'bmp', 'dng', 'heic', 'heif', 'jp2', 'jpeg', 'jpeg2000', 'jpg', 'mpo', 'png', 'tif', 'tiff', 'webp'}

print(VID_FORMATS)
# {'asf', 'avi', 'gif', 'm4v', 'mkv', 'mov', 'mp4', 'mpeg', 'mpg', 'ts', 'wmv', 'webm'}

Link to this sectionRendi divisibile#

Calcola il numero intero più piccolo maggiore o uguale a x che sia divisibile per y.

from ultralytics.utils.ops import make_divisible

make_divisible(7, 3)
# >>> 9
make_divisible(7, 2)
# >>> 8

Link to this sectionFAQ#

Link to this sectionQuali utility sono incluse nel pacchetto Ultralytics per migliorare i flussi di lavoro di machine learning?#

Il pacchetto Ultralytics include utility progettate per snellire e ottimizzare i flussi di lavoro di machine learning. Le utility chiave includono l'auto-annotazione per etichettare i dataset, la conversione di COCO in formato YOLO con convert_coco, la compressione di immagini e l'auto-split del dataset. Questi strumenti riducono lo sforzo manuale, garantiscono coerenza e migliorano l'efficienza di elaborazione dei dati.

Link to this sectionCome posso usare Ultralytics per auto-etichettare il mio dataset?#

Se hai un modello di object detection Ultralytics YOLO pre-addestrato, puoi usarlo con il modello SAM per auto-annotare il tuo dataset in formato di segmentazione. Ecco un esempio:

from ultralytics.data.annotator import auto_annotate

auto_annotate(
    data="path/to/new/data",
    det_model="yolo26n.pt",
    sam_model="mobile_sam.pt",
    device="cuda",
    output_dir="path/to/save_labels",
)

Per ulteriori dettagli, consulta la sezione di riferimento auto_annotate, oppure usa Ultralytics Platform come alternativa ospitata e senza codice con mascheramento basato su clic tramite SAM 2.1 o SAM 3, o previsioni da modelli YOLO pre-addestrati e fine-tuned per compiti di detect, segment e OBB.

Link to this sectionCome converto le annotazioni del dataset COCO in formato YOLO in Ultralytics?#

Per convertire le annotazioni JSON COCO nel formato YOLO per l'object detection, puoi usare l'utility convert_coco. Ecco un frammento di codice di esempio:

from ultralytics.data.converter import convert_coco

convert_coco(
    "coco/annotations/",
    use_segments=False,
    use_keypoints=False,
    cls91to80=True,
)

Per ulteriori informazioni, visita la pagina di riferimento convert_coco.

Link to this sectionCome posso analizzare la composizione e la distribuzione del mio dataset?#

Ultralytics Platform fornisce analisi automatiche del dataset: la scheda Charts mostra la distribuzione dello split, i conteggi delle classi principali, gli istogrammi delle dimensioni delle immagini e le mappe di calore 2D delle posizioni delle annotazioni, aiutandoti a individuare squilibri e outlier prima dell'addestramento.

Link to this sectionCome posso convertire i bounding box in segmenti in Ultralytics?#

Per convertire i dati dei bounding box esistenti (in formato x y w h) in segmenti, puoi usare la funzione yolo_bbox2segment. Assicurati che i tuoi file siano organizzati con directory separate per immagini e label.

from ultralytics.data.converter import yolo_bbox2segment

yolo_bbox2segment(
    im_dir="path/to/images",
    save_dir=None,  # saved to "labels-segment" in the images directory
    sam_model="sam_b.pt",
)

Per maggiori informazioni, visita la pagina di riferimento yolo_bbox2segment.

Commenti