EP07_05 — 🔴 Istogramma delle Orientazioni di una Cella HOG
7.18.5 EP07_05 🔴 Istogramma delle Orientazioni di una Cella HOG
La funzione hog di scikit-image, impiegata nel progetto di classificazione delle cifre, divide l’immagine in piccole celle e, per ciascuna, costruisce un istogramma delle orientazioni del gradiente ponderato per la magnitudine — esattamente il passaggio centrale descritto nella sezione sul descrittore HOG del capitolo.
Sei stato incaricato di implementare questo calcolo per una singola cella, a partire dai valori di magnitudine e orientazione del gradiente già calcolati per ogni pixel della cella (tralasciando il calcolo delle derivate parziali).
7.18.5.1 📋 Linee Guida di Implementazione
Dimensioni: Leggere gli interi \(n\) (la cella ha \(n \times n\) pixel) e \(B\) (numero di contenitori dell’istogramma).
Magnitudini: Leggere \(n\) righe con \(n\) valori reali ciascuna, che rappresentano \(|\nabla f(x,y)|\) per ogni pixel della cella.
Orientazioni: Leggere altre \(n\) righe con \(n\) valori reali ciascuna, che rappresentano \(\theta(x,y)\) in gradi, già convertiti nell’intervallo non orientato\([0^\circ, 180^\circ)\), come convenzionalmente utilizzato dal HOG.
Contenitori: I \(B\) contenitori coprono \([0^\circ, 180^\circ)\) in fasce uguali di larghezza \(180/B\) gradi. Un pixel con orientazione \(\theta\) appartiene al contenitore \(\lfloor \theta / (180/B) \rfloor\); se questo indice è uguale a \(B\) (possibile solo quando \(\theta\) è esattamente \(180^\circ\), cosa che non dovrebbe verificarsi secondo la direttiva del punto 3), utilizzare il contenitore \(B-1\).
Istogramma grezzo: Per ogni pixel, accumulare la sua magnitudine (non il suo conteggio) nel contenitore corrispondente: \[
H[b] = \sum_{(x,y)\, :\, \text{bin}(\theta(x,y)) = b} |\nabla f(x,y)|.
\]
Normalizzazione L2: Dopo aver costruito \(H\), normalizzarlo per ottenere \(\hat H\): \[
\hat H[b] = \frac{H[b]}{\sqrt{\sum_{j=0}^{B-1} H[j]^2 + \epsilon}}, \qquad \epsilon = 10^{-6}.
\]
Output: Stampare l’istogramma grezzo \(H\) (arrotondato a 2 cifre decimali) su una riga, seguito dall’istogramma normalizzato \(\hat H\) (arrotondato a 4 cifre decimali) su un’altra riga, entrambi con i \(B\) valori separati da spazi, nell’ordine dei contenitori.
7.18.5.2 📌 Vincoli Computazionali
Binning non orientato: l’intervallo delle orientazioni è \([0,180)\), non \([0,360)\) — i gradienti in direzioni opposte (differenza di \(180^\circ\)) contribuiscono allo stesso contenitore, convenzione standard del HOG per il rilevamento di oggetti.
Accumulo per magnitudine, non per conteggio: l’istogramma pondera ogni pixel per la sua magnitudine del gradiente, non conta semplicemente quanti pixel cadono in ciascun contenitore.
Costante di stabilizzazione: l’\(\epsilon = 10^{-6}\) al denominatore della normalizzazione evita la divisione per zero quando la cella è completamente omogenea (tutte le magnitudini nulle).
7.18.5.3 📐 Da dove provengono le matrici di ingresso
Prima di questo EP, ogni pixel \((x,y)\) dell’immagine passa attraverso:
Ripetendo questo per tutti i pixel di una cella \(n\times n\), si ottengono le due matrici di ingresso di questo esercizio: magnitudini\(|\nabla f|\) e orientazioni\(\theta \in [0°,180°)\).
7.18.5.4 🧠 Fondamenti Teorici
Fase
Ruolo
Magnitudine del gradiente
Pondera il contributo di ogni pixel — i bordi forti pesano più del rumore debole
Orientazione non orientata
Rende il descrittore invariante alla polarità del contrasto (chiaro→scuro vs. scuro→chiaro)
Istogramma per cella
Riassume la distribuzione locale dei bordi in un vettore compatto
Normalizzazione L2
Riduce la sensibilità del descrittore alle variazioni globali di illuminazione e contrasto
La concatenazione degli istogrammi normalizzati di tutte le celle dell’immagine — non implementata in questo esercizio — forma il vettore di caratteristiche HOG completo, utilizzato come ingresso del classificatore k-NN nel progetto del capitolo.
Riga 1: i \(B\) valori dell’istogramma grezzo, arrotondati a 2 cifre decimali.
Riga 2: i \(B\) valori dell’istogramma normalizzato, arrotondati a 4 cifre decimali.
7.18.5.6 📌 Esempi
Ingresso
Uscita
Osservazione
2 2
1.0 2.0
3.0 4.0
10 100
170 20
5.00 5.00
0.7071 0.7071
Contenitore di larghezza 90°: \([0,90)\) e \([90,180)\); le magnitudini 1 e 4 cadono nel contenitore 0, 2 e 3 nel contenitore 1.
2 4
0.0 0.0
0.0 0.0
0 0
0 0
0.00 0.00 0.00 0.00
0.0000 0.0000 0.0000 0.0000
Cella omogenea: \(\epsilon\) evita la divisione per zero.
🎮 Simulatore EP07_05: Istogramma delle Orientazioni di una Cella🔴 cella 3×3 fissa
Regola B e osserva come la matrice delle orientazioni (indipendente da quella delle magnitudini) viene mappata
nei compartimenti tramite bin = floor(θ / (180/B)), e come le magnitudini vengono sommate in ciascun bin.
2
📄 Input (esattamente come il programma legge da stdin)
🔢 Matrice delle magnitudini |∇f|
📐 Matrice delle orientazioni θ (gradi) — colorata per bin
📏 Dove ciascun θ cade sul righello [0°, 180°) — bin = floor(θ / larghezza)
📊 Intervalli di ciascun compartimento (larghezza = 180° / B)
🧩 Ogni pixel: magnitudine + orientazione → bin
🧮 Calcolo passo passo (floor della divisione + somma delle magnitudini per bin)
Figura 7.25: Simulatore EP07_05: Istogramma HOG di una Cella (mappatura degli angoli ai bins)
%%writefile EP07_05.py# Codice Python
Overwriting EP07_05.py
TestSuite("EP07_05.py").run()
✔️ EP07_05.cases esiste già in casos/
📋 5 caso/i caricato/i da casos/EP07_05.cases
🔍 Test di Python: EP07_05.py
⚠️ EP07_05.py: file vuoto (meno di 3 righe). Test saltati.