Ultralytics YOLO27: Iscriviti alla lista d'attesa.
Get Started
Fondamenti della visione artificiale·Scegli un task·Lezione 5/10
Lezioneprincipiante

Stima della posa e OBB

Leggi i keypoint e i riquadri ruotati da YOLO26, definisci una regola basata su ciascuno e riconosci quando il segnale determinante è la postura o l’angolo.

Una casa di riposo deve sapere quando qualcuno è caduto; un porto deve contare le navi affiancate in un’immagine ripresa da un drone. I riquadri standard non funzionano in nessuno dei due casi: un riquadro non indica se una persona è in piedi e un riquadro verticale attorno a una nave diagonale contiene perlopiù acqua. La stima della posa e gli OBB sono pensati proprio per questi due problemi.

Esito

Definisci una regola sulla postura a partire dai keypoint di YOLO26 e misura quanto fanno risparmiare i riquadri ruotati nelle immagini aeree.

Percorso rapido
Se sai già come muoverti, ecco la versione breve.
  1. Pose: un riquadro più 17 keypoint per persona (ordine COCO: 0 naso, 5–6 spalle, 11–12 anche, 15–16 caviglie).

  2. Filtra i keypoint in base alla confidenza prima di usarli; anche le articolazioni nascoste hanno comunque delle coordinate.

  3. OBB: centro, dimensioni e angolo (xywhr, angolo in radianti).

  4. Usa la stima della posa quando il segnale è la postura; gli OBB quando gli oggetti sono inclinati nelle viste dall’alto; altrimenti usa il rilevamento.

Pratico

Pose: quando il segnale è la postura#

Tre corridori su un percorso lungo il lungomare, ciascuno con un riquadro intorno alla persona e uno scheletro con 17 keypoint ottenuto con la stima della posa di Ultralytics YOLO

Un modello di stima della posa restituisce un riquadro per ogni persona e un elenco fisso di keypoint. I modelli addestrati su COCO-Pose prevedono 17 keypoint per persona — naso, occhi, orecchie, spalle, gomiti, polsi, anche, ginocchia e caviglie — sempre nello stesso ordine: l’indice 0 è il naso, l’11 l’anca sinistra e il 15 la caviglia sinistra. Ogni keypoint ha anche un valore di confidenza.

La regola utile più semplice: un corpo in piedi è più alto che largo; un corpo disteso sul pavimento è più largo che alto. Ecco il risultato sull’immagine dell’autobus, usando solo i keypoint di cui il modello è sicuro:

from ultralytics import YOLO

model = YOLO("yolo26n-pose.pt")
result = model("https://ultralytics.com/images/bus.jpg", verbose=False)[0]

for xy, conf in zip(result.keypoints.xy, result.keypoints.conf):
    visible = xy[conf > 0.5]  # drop keypoints the model couldn't see
    width = float(visible[:, 0].max() - visible[:, 0].min())
    height = float(visible[:, 1].max() - visible[:, 1].min())
    posture = "unknown" if len(visible) < 5 else "lying" if width > height else "upright"
    print(f"{len(visible):2d}/17 keypoints visible, body {width:3.0f} px wide x {height:3.0f} px tall -> {posture}")
16/17 keypoints visible, body 117 px wide x 427 px tall -> upright
 6/17 keypoints visible, body  80 px wide x 359 px tall -> upright
16/17 keypoints visible, body  91 px wide x 384 px tall -> upright
 1/17 keypoints visible, body   0 px wide x   0 px tall -> unknown
 2/17 keypoints visible, body   3 px wide x   6 px tall -> unknown

Tre persone sono chiaramente in piedi. Le ultime due righe corrispondono alla persona tagliata sul bordo sinistro e a un duplicato con bassa confidenza: con uno o due keypoint visibili non c’è abbastanza per giudicare, quindi la regola restituisce «sconosciuto» invece di tirare a indovinare. Un rilevatore di cadute pronto per la produzione aggiunge la dimensione temporale — la persona deve restare distesa per più di qualche secondo, dopo una caduta rapida — tramite il tracciamento.

Anche le articolazioni nascoste hanno coordinate

Sintomo: scheletri con i polsi sospesi nel vuoto e regole sulla postura che si attivano con persone visibili solo in parte. Causa: keypoints.xy restituisce una posizione per tutti e 17 i keypoint, compresi quelli che il modello non è riuscito a vedere. Soluzione: filtra con keypoints.conf, come sopra, e richiedi un numero minimo di keypoint visibili prima di prendere una decisione.

La stima della posa è utile quando la risposta dipende da ciò che fa il corpo: cadute o sollevamenti con la schiena piegata per la sicurezza, angoli delle articolazioni e conteggio delle ripetizioni nello sport, come nel monitoraggio degli allenamenti, oppure postura del bestiame e punti di riferimento fissi su componenti con una disposizione personalizzata dei keypoint. Per rispondere a «c’è una persona qui?», usa il rilevamento standard.

OBB: quando l’angolo conta#

Tre yacht ormeggiati con diverse inclinazioni in un’immagine aerea, ciascuno racchiuso in un riquadro ruotato aderente ottenuto con Ultralytics YOLO OBB

I lati di un riquadro standard sono paralleli all’immagine. Un riquadro di delimitazione orientato aggiunge una rotazione, rappresentata da centro, larghezza, altezza e angolo (xywhr). Nelle immagini dall’alto — satellitari, riprese da droni o con telecamere sopra i nastri trasportatori — gli oggetti sono orientati in ogni direzione e un riquadro verticale intorno a un oggetto diagonale contiene perlopiù sfondo, come accadrebbe con gli yacht qui sopra. Misura la differenza su una ripresa con drone di un porto turistico:

from ultralytics import YOLO

model = YOLO("yolo26n-obb.pt")
result = model("https://ultralytics.com/images/boats.jpg", verbose=False)[0]

obb = result.obb
rotated_area = obb.xywhr[:, 2] * obb.xywhr[:, 3]  # width x height of each rotated box
x1, y1, x2, y2 = obb.xyxy.T  # the axis-aligned box that would enclose the same object
upright_area = (x2 - x1) * (y2 - y1)

print(f"{len(obb)} objects, classes: {sorted({result.names[int(c)] for c in obb.cls})}")
cx, cy, w, h, angle = obb.xywhr[0].tolist()
print(f"first box: center=({cx:.0f}, {cy:.0f}) size={w:.0f}x{h:.0f} angle={angle:.2f} rad")
ratio = float((upright_area / rotated_area).median())
print(f"an axis-aligned box would be {ratio:.1f}x larger (median)")
173 objects, classes: ['harbor', 'ship']
first box: center=(619, 850) size=33x108 angle=-0.25 rad
an axis-aligned box would be 2.1x larger (median)

Un riquadro verticale copre circa il doppio dell’area rispetto al riquadro ruotato attorno alla stessa barca, e l’area in più è acqua. Questo causa due problemi: NMS rileva la sovrapposizione tra i riquadri verticali delle barche vicine e potrebbe eliminare rilevamenti corretti; inoltre, qualsiasi stima delle dimensioni risulta sovrastimata. I modelli OBB addestrati su dataset aerei come DOTA gestiscono direttamente queste scene. Nota che l’angolo è espresso in radianti: -0.25 rad corrisponde a circa -14°.

Scegliere tra rilevamento, stima della posa e OBB#

ScenarioAttività più adattaPerché
Contare le persone su un marciapiedeRilevamentoLa risposta è la presenza e la posizione
Rilevare una caduta in una casa di riposoStima della posaIl segnale è l’orientamento del corpo
Contare gli squat in palestraStima della posaIl segnale sono gli angoli di ginocchia e anche
Contare le barche ormeggiate riprese da un droneOBBLe barche sono disposte in diagonale e ravvicinate
Pacchi su un nastro trasportatore, ripresi dall’altoOBBL’orientamento varia e gli oggetti vicini si toccano
Auto a livello della stradaRilevamentoLe auto appaiono più o meno verticali nell’inquadratura
Pose e OBB sono il rilevamento più un elemento

Pose aggiunge keypoint a ogni riquadro; OBB aggiunge un angolo. Se il tuo codice non legge mai i keypoint o l'angolo, un semplice rilevatore è più rapido da etichettare, da eseguire e più facile da correggere.

Provalo

Esegui il confronto della soluzione sull’immagine del porto turistico: il rilevatore preaddestrato su COCO e il modello OBB. Annota entrambi i conteggi, poi scrivi una frase per spiegare quanta parte della differenza dipende dalla geometria dei riquadri e quanta dai dati su cui è stato addestrato ciascun modello. Infine, indica un problema del tuo lavoro in cui la stima della posa o gli OBB sarebbero più efficaci del rilevamento standard e la regola che applicherebbe il tuo codice.

Criteri di completamento
La lezione è completata quando tutte le seguenti condizioni sono soddisfatte.
  • Hai entrambi i conteggi su boats.jpg e una spiegazione, in una frase, della differenza.

  • Sai indicare la riga della regola sulla postura che filtra i keypoint nascosti e spiegare perché è necessaria.

  • Hai indicato un problema del tuo lavoro per cui useresti la stima della posa o gli OBB, insieme alla regola che applicherebbe il tuo codice.

Mostra la soluzione
from ultralytics import YOLO

image = "https://ultralytics.com/images/boats.jpg"
upright = YOLO("yolo26n.pt")(image, verbose=False)[0]
rotated = YOLO("yolo26n-obb.pt")(image, verbose=False)[0]
print(f"axis-aligned detector: {len(upright.boxes)} boxes")
print(f"OBB model: {len(rotated.obb)} rotated boxes")
axis-aligned detector: 0 boxes
OBB model: 173 rotated boxes

La maggior parte della differenza dipende dai dati di addestramento, non dalla geometria. yolo26n.pt è stato addestrato su COCO, dove le barche sono perlopiù fotografate di lato; dall’alto non rileva nulla con la soglia predefinita (abbassa conf a 0.05 e ne identifica alcune come bottiglie). Il modello OBB è stato addestrato su immagini aeree. Anche la geometria conta: persino un rilevatore addestrato su immagini aeree di barche disegnerebbe riquadri circa due volte più grandi e avrebbe difficoltà con NMS in file molto ravvicinate. Sia l’attività sia i dati di addestramento devono corrispondere alla vista prevista in produzione.

Prossimi passi

Il porto turistico ha mostrato che i dati di addestramento contano tanto quanto l’attività. Prossimo argomento: verificare se un dataset corrisponde al mondo in cui lo userai.

Accedi per salvare i progressi