- 1. Segmentazione e contorni
- 2. Gerarchia e modalità di recupero
- 3. Approssimare i contorni e trovare il loro scafo convesso
- 4. Scafo convesso
- 5. Contorno di corrispondenza per forme
- 6. Identificazione delle forme (cerchio, rettangolo, triangolo, quadrato, stella)
- 7. Rilevamento della linea
- 8. Rilevamento blob
- 9. Filtraggio dei blob - Conteggio di cerchi ed ellissi
Nei tutorial precedenti, abbiamo utilizzato OpenCV per l'elaborazione di immagini di base e abbiamo eseguito alcune operazioni avanzate di modifica delle immagini. Come sappiamo, OpenCV è Open Source Commuter Vision Library che ha interfacce C ++, Python e Java e supporta Windows, Linux, Mac OS, iOS e Android. Quindi può essere facilmente installato in Raspberry Pi con Python e ambiente Linux. E Raspberry Pi con OpenCV e telecamera collegata può essere utilizzato per creare molte applicazioni di elaborazione delle immagini in tempo reale come Face detection, Face Lock, Object Tracking, Rilevamento targa auto, Sistema di sicurezza domestica, ecc. In questo tutorial impareremo come fare segmentazione delle immagini utilizzando OpenCV. Le operazioni che andremo a eseguire sono elencate di seguito:
- Segmentazione e contorni
- Gerarchia e modalità di recupero
- Avvicinando i contorni e trovando il loro scafo convesso
- Scafo Conex
- Contorno abbinato
- Identificazione delle forme (cerchio, rettangolo, triangolo, quadrato, stella)
- Rilevamento della linea
- Rilevamento blob
- Filtrare le macchie - contare cerchi ed ellissi
1. Segmentazione e contorni
La segmentazione delle immagini è un processo mediante il quale partizioniamo le immagini in diverse regioni. Mentre i contorni sono le linee o le curve continue che delimitano o coprono l'intero confine di un oggetto in un'immagine. E qui useremo la tecnica di segmentazione dell'immagine chiamata contorni per estrarre le parti di un'immagine.
Anche i contorni sono molto importanti in
- Rilevamento di oggetti
- Analisi della forma
E hanno un campo di applicazione molto ampio, dall'analisi delle immagini del mondo reale all'analisi delle immagini mediche come nella risonanza magnetica
Sappiamo come implementare i contorni in opencv, estraendo i contorni dei quadrati.
importa cv2 importa numpy come np
Carichiamo una semplice immagine con 3 quadrati neri
image = cv2.imread ('squares.jpg') cv2.imshow ('input image', image) cv2.waitKey (0)
Scala di grigi
gray = cv2.cvtColor (immagine, cv2.COLOR_BGR2GRAY)
Trova bordi sottili
bordo = cv2.Canny (grigio, 30.200) cv2.imshow ('bordi canny ', bordo) cv2.waitKey (0)
Trovare contorni
# usa una copia della tua immagine, ad esempio - edged.copy (), poiché la ricerca dei contorni altera l'immagine #dobbiamo aggiungere _, prima dei contorni come argomento vuoto a causa dell'aggiornamento della versione OpenCV _, contorni, gerarchia = cv2.findContours (edged, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE) cv2.imshow (' canny edge after contouring', edged) cv2.waitKey (0)
Stampa il file del contorno per sapere di cosa sono composti i contorni
print (contorni) print ('Numeri di contorni trovati =' + str (len (contorni)))
Disegna tutti i contorni
# usa -1 come terzo parametro per disegnare tutti i contorni cv2.drawContours (image, contours, -1, (0,255,0), 3) cv2.imshow ('contours', image) cv2.waitKey (0) cv2. distruggereAllWindows ()
Uscita console -],],], …,],],]], dtype = int32), Vettore(],],
], …,
],],]], dtype = int32), array (],],], …,],],]], dtype = int32)]
Numero di contorni trovati = 3. Quindi abbiamo trovato un totale di tre contorni.
Ora, nel codice sopra abbiamo anche stampato il file di contorno usando , questo file dice come appaiono questi contorni, come stampato nell'output della console sopra.
Nell'output della console sopra abbiamo una matrice che assomiglia a coordinate di punti x, y. OpenCV memorizza i contorni in elenchi di elenchi. Possiamo semplicemente mostrare l'output della console sopra come segue:
CONTOUR 1 CONTOUR 2 CONTOUR 3
], array (], array (],],],],],],],
…,…,…,],],],],],],]], dtype = int32),]], dtype = int32),]], dtype = int32)]
Ora, poiché utilizziamo la funzione di lunghezza sul file di contorno, otteniamo la lunghezza uguale a 3, significa che c'erano tre elenchi di elenchi in quel file, cioè tre contorni.
Ora, immagina CONTOUR 1 sia il primo elemento in quell'array e quell'elenco contiene l'elenco di tutte le coordinate e queste coordinate sono i punti lungo i contorni che abbiamo appena visto, come le caselle rettangolari verdi.
Esistono diversi metodi per memorizzare queste coordinate e questi sono chiamati metodi di approssimazione, fondamentalmente i metodi di approssimazione sono di due tipi
- cv2.CHAIN_APPROX_NONE
- cv2.CHAIN_APPROX_SIMPLE
cv2.CHAIN_APPROX_NONE memorizza tutto il punto di confine, ma non abbiamo necessariamente bisogno di tutti i punti di confine, se il punto forma una linea retta, abbiamo solo bisogno del punto iniziale e del punto finale su quella linea.
cv2.CHAIN_APPROX_SIMPLE invece fornisce solo i punti iniziale e finale dei contorni di delimitazione, il risultato è una memorizzazione molto più efficiente delle informazioni di contorno.
_, contorni, gerarchia = cv2.findContours (edged, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE)
Nel codice sopra cv2.RETR_EXTERNAL è la modalità di recupero mentre cv2.CHAIN_APPROX_NONE è
il metodo di approssimazione.
Quindi abbiamo imparato a conoscere i contorni e il metodo di approssimazione, ora esploriamo la gerarchia e la modalità di recupero.
2. Gerarchia e modalità di recupero
La modalità Recupero definisce la gerarchia in contorni come contorni secondari o contorno esterno o tutti i contorni.
Ora ci sono quattro modalità di recupero ordinate in base ai tipi di gerarchia.
cv2.RETR_LIST - recupera tutti i contorni.
cv2.RETR_EXTERNAL - recupera solo i contorni esterni o esterni.
cv2.RETR_CCOMP - recupera tutto in una gerarchia a 2 livelli.
cv2.RETR_TREE - recupera tutto in una gerarchia completa.
La gerarchia è archiviata nel formato seguente
Ora illustriamo la differenza tra le prime due modalità di recupero, cv2.RETR_LIST e cv2.RETR_EXTERNAL.
importa cv2 importa numpy come np
Consente di caricare una semplice immagine con 3 quadrati neri
immagine = cv2.imread ('square donut.jpg') cv2.imshow ('input image', image) cv2.waitKey (0)
Scala di grigi
gray = cv2.cvtColor (immagine, cv2.COLOR_BGR2GRAY)
Trova Canny Edges
bordo = cv2.Canny (grigio, 30.200) cv2.imshow ('bordi canny ', bordo) cv2.waitKey (0)
Trovare contorni
# usa una copia della tua immagine, ad esempio - edged.copy (), poiché la ricerca di contorni altera l'immagine #dobbiamo aggiungere _, prima dei contorni come argomento vuoto a causa dell'aggiornamento della versione cv aperta _, contorni, gerarchia = cv2.findContours (edged, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE) cv2.imshow (' canny edge after contouring', edged) cv2.waitKey (0)
Stampa il file del contorno per sapere di cosa sono composti i contorni.
print (contorni) print ('Numeri di contorni trovati =' + str (len (contorni)))
Disegna tutti i contorni
# usa -1 come terzo parametro per disegnare tutti i contorni cv2.drawContours (image, contours, -1, (0,255,0), 3) cv2.imshow ('contours', image) cv2.waitKey (0) cv2. destroyAllWindows
importa cv2 importa numpy come np
Consente di caricare una semplice immagine con 3 quadrati neri
immagine = cv2.imread ('square donut.jpg') cv2.imshow ('input image', image) cv2.waitKey (0)
Scala di grigi
gray = cv2.cvtColor (immagine, cv2.COLOR_BGR2GRAY)
Trova bordi sottili
bordo = cv2.Canny (grigio, 30.200) cv2.imshow ('bordi canny ', bordo) cv2.waitKey (0)
Trovare contorni
# usa una copia della tua immagine, ad esempio - edged.copy (), poiché la ricerca di contorni altera l'immagine #dobbiamo aggiungere _, prima dei contorni come argomento vuoto a causa dell'aggiornamento della versione cv aperta _, contorni, gerarchia = cv2.findContours (edged, cv2.RETR_LIST, cv2.CHAIN_APPROX_NONE) cv2.imshow (' canny edge after contouring', edged) cv2.waitKey (0)
Stampa il file del contorno per sapere di cosa sono composti i contorni.
print (contorni) print ('Numeri di contorni trovati =' + str (len (contorni)))
Disegna tutti i contorni
# usa -1 come terzo parametro per disegnare tutti i contorni cv2.drawContours (image, contours, -1, (0,255,0), 3) cv2.imshow ('contours', image) cv2.waitKey (0) cv2. distruggereAllWindows ()
Quindi attraverso la dimostrazione dei codici sopra abbiamo potuto vedere chiaramente la differenza tra cv2.RETR_LIST e cv2.RETR_EXTERNNAL , in cv2.RETR_EXTERNNAL vengono presi in considerazione solo i contorni esterni mentre i contorni interni vengono ignorati.
Mentre in cv2.RETR_LIST vengono presi in considerazione anche i contorni interni.
3. Approssimare i contorni e trovare il loro scafo convesso
Nell'approssimare i contorni, una forma del contorno viene approssimata su un'altra forma del contorno, che potrebbe non essere molto simile alla prima forma del contorno.
Per approssimazione usiamo approxPolyDP funzione OpenCV illustrata di seguito
cv2.approxPolyDP (contorno, precisione di approssimazione, chiuso)
Parametri:
- Contorno - è il contorno individuale che desideriamo approssimare.
- Precisione di approssimazione: parametro importante per determinare l'accuratezza di approssimazione, valori piccoli danno un'approssimazione precisa, valori grandi forniscono informazioni più generiche. Una buona regola empirica è inferiore al 5% del perimetro del contorno.
- Chiuso: un valore booleano che indica se il contorno approssimativo può essere aperto o chiuso.
Proviamo ad approssimare una semplice figura di una casa
importa numpy come np importa cv2
Carica l'immagine e conserva una copia
image = cv2.imread ('house.jpg') orig_image = image.copy () cv2.imshow ('immagine originale', orig_image) cv2.waitKey (0)
Scala di grigi e binarizza l'immagine
grigio = cv2.cvtColor (immagine, cv2.COLOR_BGR2GRAY) ret, thresh = cv2.threshold (grigio, 127,255, cv2.THRESH_BINARY_INV)
Trova contorni
_, contorni, gerarchia = cv2.findContours (thresh.copy (), cv2.RETR_LIST, cv2.CHAIN_APPROX_NONE)
Itera attraverso ogni contorno e calcola il loro rettangolo di delimitazione
per c nei contorni: x, y, w, h = cv2.boundingRect (c) cv2.rectangle (orig_image, (x, y), (x + w, y + h), (0,0,255), 2) cv2.imshow ('Bounding rect', orig_image) cv2.waitKey (0)
Itera attraverso ogni contorno e calcola il contorno approssimativo
per c in contorni:
# calcola la precisione come percentuale della precisione del perimetro del contorno = 0,03 * cv2.arcLength (c, True) approx = cv2.approxPolyDP (c, accuratezza, True) cv2.drawContours (image`` 0, (0,255,0), 2) cv2.imshow ('Approx polyDP', immagine) cv2.waitKey (0) cv2.destroyAllWindows ()
4. Scafo convesso
Lo scafo convesso è fondamentalmente i bordi esterni, rappresentati disegnando linee su una data figura.
Potrebbe essere il poligono più piccolo che può adattarsi all'oggetto stesso.
importa cv2 importa numpy come immagine np = cv2.imread ('star.jpg') gray = cv2.cvtColor (immagine, cv2.COLOR_BGR2GRAY) cv2.imshow ('immagine originale', immagine) cv2.waitKey (0)
Soglia l'immagine
ret, thresh = cv2.threshold (grigio, 176,255,0)
Trova i contorni
_, contorni, gerarchia = cv2.findContours (thresh.copy (), cv2.RETR_LIST, cv2.CHAIN_APPROX_NONE)
Ordinare i contorni per area e quindi rimuovere il contorno della cornice più grande
n = len (contorni) -1 contorni = ordinati (contorni, chiave = cv2.contourArea, reverse = False)
Itera attraverso i contorni e disegna lo scafo convesso
per c in contorni:
hull = cv2.convexHull (c) cv2.drawContours (image,, 0, (0,255,0), 2) cv2.imshow ('convex hull', image) cv2.waitKey (0) cv2.destroyAllWindows ()
5. Contorno di corrispondenza per forme
cv2.matchShapes (modello di contorno, metodo di contorno, parametro del metodo)
Risultato: valore di corrispondenza (un valore inferiore indica una corrispondenza più ravvicinata)
modello di contorno - Questo è il nostro contorno di riferimento che stiamo cercando di trovare in una nuova immagine.
contorno - Il contorno individuale che stiamo controllando.
Metodo - Tipo di adattamento del contorno (1,2,3).
parametro del metodo: lasciare da solo 0.0 (non utilizzato in python opencv)
importa cv2 importa numpy come np
Carica il modello di forma o l'immagine di riferimento
template = cv2.imread ('star.jpg', 0) cv2.imshow ('template', template) cv2.waitKey (0)
Carica l'immagine di destinazione con le forme che stiamo cercando di abbinare
target = cv2.imread ('shapestomatch.jpg') gray = cv2.cvtColor (target, cv2.COLOR_BGR2GRAY)
Soglia entrambe le immagini prima di utilizzare cv2.findContours
ret, thresh1 = cv2.threshold (modello, 127,255,0) ret, thresh2 = cv2.threshold (grigio, 127,255,0)
Trova i contorni nel modello
_, contours, hierarhy = cv2.findContours (thresh1, cv2.RETR_CCOMP, cv2.CHAIN_APPROX_SIMPLE) #dobbiamo ordinare i contorni per area in modo da poter rimuovere il contorno più grande che è
Profilo dell'immagine
ordinato_contours = ordinato (contorni, chiave = cv2.contourArea, reverse = True) # estraiamo il secondo contorno più grande che sarà il nostro contorno modello tempelate_contour = contorni #estrazione dei contorni dalla seconda immagine di destinazione _, contorni, gerarchia = cv2.findContours (thresh2, cv2.RETR_CCOMP, cv2.CHAIN_APPROX_SIMPLE) for c in contours: #iterate through each contour in the target image and use cv2.matchShape to compare the contour shape match = cv2.matchShapes (tempelate_contour, c, 1,0.0) print ("match") #if valore di corrispondenza è inferiore a 0,15 se corrispondenza <0,16: più vicino_contour = c else: più vicino_contour = cv2.drawContours (target,, - 1, (0,255,0), 3) cv2.imshow ('output',bersaglio) cv2.waitKey (0) cv2.destroyAllWindows ()
Uscita console -
0.16818605122199104
0.19946910256158912
0.18949760627309664
0.11101058276281539
Esistono tre metodi diversi con diverse funzioni matematiche, possiamo sperimentare ogni metodo semplicemente sostituendo i valori del metodo cv2.matchShapes (tempelate_contour, c, 1, 0.0) che varia da 1,2 e 3, per ogni valore otterrai una corrispondenza diversa valori nell'output della console.
6. Identificazione delle forme (cerchio, rettangolo, triangolo, quadrato, stella)
OpenCV può anche essere utilizzato per rilevare automaticamente diversi tipi di forme dall'immagine. Utilizzando il codice sottostante saremo in grado di rilevare cerchi, rettangoli, triangoli, quadrati e stelle dall'immagine.
importa cv2 importa numpy come np
Carica e poi immagini in scala di grigi
immagine = cv2.imread ('shapes.jpg') gray = cv2.cvtColor (image, cv2.COLOR_BGR2GRAY) cv2.imshow ('identificazione delle forme', immagine) cv2.waitKey (0) ret, thresh = cv2.threshold (grigio, 127,255,1)
Estrai contorni
_, contorni, gerarchia = cv2.findContours (thresh.copy (), cv2.RETR_LIST, cv2.CHAIN_APPROX_NONE)
Per cnt in contours:
Ottieni poligoni approssimativi approx = cv2.approxPolyDP (cnt, 0.01 * cv2.arcLength (cnt, True), True) if len (approx) == 3: shape_name = "Triangle" cv2.drawContours (image,, 0, (0,255, 0), - 1)
trova il centro del contorno per posizionare il testo al centro
M = cv2.moments (cnt) cx = int (M / M) cy = int (M / M) cv2.putText (image, shape_name, (cx-50, cy), cv2.FONT_HERSHEY_SIMPLEX, 1, (0,0, 0), 1) elif len (approx) == 4: x, y, w, h = cv2.boundingRect (cnt) M = cv2.moments (cnt) cx = int (M / M) cy = int (M / M)
Controlla se quel poligono a quattro lati è quadrato o rettangolo
# cv2.boundingRect restituisce la larghezza e l'altezza sinistra in pixel, a partire dall'angolo superiore # sinistro, per il quadrato sarebbe più o meno lo stesso se abs (wh) <= 3: shape_name = "square" #find contour center to place text at center cv2.drawContours (image,, 0, (0,125,255), - 1) cv2.putText (image, shape_name, (cx-50, cy), cv2.FONT_HERSHEY_SIMPLEX, 1, (0,0,0), 1) altro: shape_name = "Reactangle" #find contour center per posizionare il testo al centro cv2.drawContours (image,, 0, (0,0,255), - 1) M = cv2.moments (cnt) cx = int (M / M) cy = int (M / M) cv2.putText (immagine, shape_name, (cx-50, cy), cv2.FONT_HERSHEY_SIMPLEX, 1, (0,0,0), 1) elif len (approx) == 10: shape_name = 'stella' cv2.drawContours (image,, 0, (255,255,0), - 1) M = cv2.moments (cnt) cx = int (M / M) cy = int (M / M) cv2.putText (image, shape_name, (cx-50, cy), cv2.FONT_HERSHEY_SIMPLEX, 1, (0,0,0), 1) elif len (approx)> = 15: shape_name = 'circle' cv2.drawContours (immagine,, 0, (0,255,255), -1) M = cv2.moments (cnt) cx = int (M / M) cy = int (M / M) cv2.putText (image, shape_name, (cx-50, cy), cv2.FONT_HERSHEY_SIMPLEX, 1, (0,0,0), 1) cv2.imshow ('identificazione di forme', immagine) cv2.waitKey (0) cv2.destroyAllWindows ()
7. Rilevamento della linea
Il rilevamento della linea è un concetto molto importante in OpenCV e ha un uso promettente nel mondo reale. Le auto autonome utilizzano algoritmi di rilevamento della linea per il rilevamento di corsie e strade.
In linea di rilevamento ci occuperemo di due algoritmi,
- Algoritmo della linea di Hough
- Algoritmo probalistico della linea di Hough.
Potresti aver ricordato la rappresentazione della retta dalla matematica delle scuole superiori con l'equazione, y = mx + c.
Tuttavia, in OpenCV la linea è rappresentata in un altro modo
L'equazione sopra ρ = xcosӨ + ysincosӨ è la rappresentazione OpenCV della linea, in cui ρ è la distanza perpendicolare della linea dall'origine e Ө è l'angolo formato dalla normale di questa linea all'origine (misurato in radianti, dove 1pi radianti / 180 = 1 grado).
La funzione OpenCV per il rilevamento della linea è data come
cv2.HoughLines (immagine binarizzata, accuratezza ρ, accuratezza Ө, soglia), dove la soglia è il voto minimo per essere considerata una linea.
Ora rileviamo le linee per un'immagine di riquadro con l'aiuto della funzione di linea di Hough di opencv.
importa cv2 importa numpy come immagine np = cv2.imread ('box.jpg')
Scala di grigi e bordi irregolari estratti
gray = cv2.cvtColor (image, cv2.COLOR_BGR2GRAY) bordi = cv2.Canny (grigio, 100,170, apertureSize = 3)
Esegui linee di Hough usando una precisione rho di 1 pixel
# precisione theta di (np.pi / 180) che è 1 grado # soglia di linea è impostata su 240 (numero di punti sulla linea) linee = cv2.HoughLines (bordi, 1, np.pi / 180, 240) # iteriamo attraverso ogni riga e converte nel formato #richiesto da cv2.lines (cioè che richiede punti finali) per i nell'intervallo (0, len (linee)): per rho, theta in righe: a = np.cos (theta) b = np.sin (theta) x0 = a * rho y0 = b * rho x1 = int (x0 + 1000 * (- b)) y1 = int (y0 + 1000 * (a)) x2 = int (x0-1000 * (-b)) y2 = int (y0-1000 * (a)) cv2.line (immagine, (x1, y1), (x2, y2), (0,255,0), 2) cv2.imshow ('hough lines', immagine) cv2.waitKey (0) cv2.destroyAllWindows ()
Ora ripetiamo il rilevamento della linea sopra con un altro algoritmo della linea probabilistica di Hough.
L'idea alla base della linea probabilistica di Hough è di prendere un sottoinsieme casuale di punti sufficiente per il rilevamento della linea.
La funzione OpenCV per la linea probabilistica di Hough è rappresentata come cv2.HoughLinesP (immagine binarizzata, precisione ρ, precisione Ө, soglia, lunghezza minima della linea, distanza massima della linea)
Ora rileviamo le linee della scatola con l'aiuto delle linee probabilistiche di Hough.
importa cv2 importa numpy come np
Scala di grigi e bordi canny estratti
image = cv2.imread ('box.jpg') gray = cv2.cvtColor (image, cv2.COLOR_BGR2GRAY) bordi = cv2.Canny (gray, 50,150, apertureSize = 3) #di nuovo usiamo le stesse precisioni rho e theta # comunque, specifichiamo un voto minimo (punti lungo la linea) di 100 # e la lunghezza minima della linea di 5 pixel e lo spazio massimo tra le linee di 10 pixel lines = cv2.HoughLinesP (bordi, 1, np.pi / 180,100,100,10) per i nell'intervallo (0, len (righe)): per x1, y1, x2, y2 nelle righe: cv2.line (immagine, (x1, y1), (x2, y2), (0,255,0), 3) cv2. imshow ('probalistic hough lines', image) cv2.waitKey (0) cv2.destroyAllWindows
8. Rilevamento blob
I BLOB possono essere descritti come un gruppo di pixel collegati che condividono tutti una proprietà comune. Il metodo per utilizzare il rilevatore di blob OpenCV è descritto in questo diagramma di flusso.
Per disegnare i punti chiave usiamo cv2.drawKeypoints che accetta i seguenti argomenti.
cv2.drawKeypoints (immagine di input, punti chiave, blank_output_array, colore, flag)
dove potrebbe essere nelle bandiere
cv2.DRAW_MATCHES_FLAGS_DEFAULT
cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS
cv2.DRAW_MATCHES_FLAGS_DRAW_OVER_OUTIMG
cv2.DRAW_MATCHES_FLAGS_NOT_DRAW_SINGLE_POINTS
e lo spazio vuoto qui è praticamente nient'altro che uno per uno matrice di zeri
Ora eseguiamo il rilevamento delle macchie su un'immagine di girasoli, dove le macchie sarebbero le parti centrali del fiore in quanto sono comuni tra tutti i fiori.
importa cv2 importa numpy come immagine np = cv2.imread ('Sunflowers.jpg', cv2.IMREAD_GRAYSCALE)
Impostare il rilevatore con i parametri predefiniti
rilevatore = cv2.SimpleBlobDetector_create ()
Rileva i blob
keypoints = detector.detect (immagine)
Disegna i blob rilevati come cerchi rossi
# cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS assicurati che #size del cerchio corrisponda alla dimensione del blob vuoto = np.zeros ((1,1)) blob = cv2.drawKeypoints (image, keypoints, blank, (0,255,255), cv2.DRAW_MATCH_DEFAULT_FLAG)
Mostra i punti chiave
cv2.imshow ('blobs', blobs) cv2.waitKey (0) cv2.destroyAllWindows ()
Anche se il codice funziona bene, ma alcuni blob vengono persi a causa delle dimensioni irregolari dei fiori poiché i fiori nella parte anteriore sono grandi rispetto ai fiori alla fine.
9. Filtraggio dei blob - Conteggio di cerchi ed ellissi
Possiamo utilizzare parametri per filtrare i blob in base alla loro forma, dimensione e colore. Per l'utilizzo dei parametri con blob detector utilizziamo la funzione di OpenCV
cv2.SimpleBlobDetector_Params ()
Vedremo filtrare i blob principalmente in base a questi quattro parametri elencati di seguito:
La zona
params.filterByArea = True / False params.minArea = pixel params.maxArea = pixel
Circolarità
params.filterByCircularity = True / False params.minCircularity = 1 è perfetto, 0 è opposto
Convessità - Area del blob / area dello scafo convesso
params.filterByConvexity = True / False params.minConvexity = Area
Inerzia
params.filterByInertia = True / False params.minInertiaRatio = 0,01
Ora proviamo a filtrare i blob con i parametri sopra menzionati
importa cv2 importa numpy come immagine np = cv2.imread ('blobs.jpg') cv2.imshow ('immagine originale', immagine) cv2.waitKey (0)
Inizializza il rilevatore utilizzando i parametri predefiniti
rilevatore = cv2.SimpleBlobDetector_create ()
Rileva i blob
keypoints = detector.detect (immagine)
Disegna macchie sulla nostra immagine come cerchi rossi
blank = np.zeros ((1,1)) blobs = cv2.drawKeypoints (image, keypoints, blank, (0,0,255), cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS) number_of_blobs = len (keypoints) text = "numero totale di blob" + str (len (keypoints)) cv2.putText (blob, text, (20,550), cv2.FONT_HERSHEY_SIMPLEX, 1, (100,0,255), 2)
Visualizza immagine con punti chiave BLOB
cv2.imshow ('blob using default parameters', blobs) cv2.waitKey (0)
Imposta i nostri parametri di filtraggio
#initialize impostazione del parametro utilizzando cv2.SimpleBlobDetector params = cv2.SimpleBlobDetector_Params ()
Imposta i parametri di filtraggio dell'area
params.filterByArea = True params.minArea = 100
Imposta i parametri di filtraggio della circolarità
params.filterByCircularity = True params.minCircularity = 0.9
Imposta il parametro di filtraggio della convessità
params.filterByConvexity = False params.minConvexity = 0.2
Imposta il parametro di filtraggio inerziale
params.filterByInertia = True params.minInertiaRatio = 0,01
Crea rilevatore con parametro
detector = cv2.SimpleBlobDetector_create (params)
Rileva i blob
keypoints = detector.detect (immagine)
Disegna macchie sulle immagini come cerchi rossi
blank = np.zeros ((1,1)) blobs = cv2.drawKeypoints (image, keypoints, blank, (0,255,0), cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS) number_of_blobs = len (keypoints) text = "numero totale di blob circolari" + str (len (keypoints)) cv2.putText (blobs, text, (20,550), cv2.FONT_HERSHEY_SIMPLEX, 1, (0,100,255), 2)
Mostra i BLOB
cv2.imshow ('filtraggio di blob circolari', blob) cv2.waitKey (0) cv2.destroyAllWindows ()
Quindi è così che può essere eseguita la segmentazione delle immagini in Python-OpenCV. Per capire bene la visione artificiale e OpenCV, consulta gli articoli precedenti (Iniziare con Python OpenCV e Manipolazioni di immagini in Python OpenCV e sarai in grado di creare qualcosa di interessante con Computer Vision.