- Tárgyfelismerés SIFT segítségével
- Tárgyfelismerés ORB segítségével
- Orientált gradiensek hisztogramja
- A orientált színátmenetek hisztogramja, lépésről lépésre:
- HAAR kaszkád osztályozók
- Arc- és szemérzékelés
- Élő arc- és szemérzékelés
- Kaszkád osztályozók beállítása
- Autók és gyalogosok észlelése videókban
Először a Python OpenCV telepítésével kezdtük el a Windows rendszert, és eddig elvégeztünk néhány alapvető képfeldolgozást, képszegmentálást és tárgyfelismerést a Python használatával, amelyekre az alábbi oktatóanyagok foglalkoznak:
- A Python OpenCV használatának megkezdése: Telepítés és alapvető képfeldolgozás
- Képmanipulációk a Python OpenCV programban (1. rész)
- Képmanipulációk az OpenCV-ben (2. rész)
- Képszegmentálás OpenCV használatával - A kép meghatározott területeinek kibontása
Ismerkedtünk az Object Detection különféle módszereivel és algoritmusaival is, ahol minden objektumhoz különféle algoritmusokat használva azonosítottunk néhány kulcspontot. Ebben az oktatóanyagban ezeket az algoritmusokat fogjuk használni a valós objektumok felderítésére, itt a SIFT és az ORB elemeket használnánk az észleléshez.
Tárgyfelismerés SIFT segítségével
Itt az objektum észlelését élő webkamera közvetítéssel végzik, így ha felismeri az objektumot, akkor megemlíti a talált objektumot. A kódban a fő részt a SIFT detektornak hívott funkció játssza, a feldolgozás nagy részét ez a funkció végzi.
A kód másik felében pedig kezdjük a webkamera-adatfolyam megnyitásával, majd töltsük be a képsablont, vagyis a referenciaképet, vagyis a program valójában a webkamera-adatfolyamot nézi át.
Ezután folyamatosan rögzítjük a képeket a webkamera adatfolyamából a végtelen, míg a hurok segítségével, majd rögzítjük a webkamera keretének megfelelő magasságát és szélességét, majd meghatározzuk az érdekes régió (ROI) mező paramétereit, amelyben objektumunk befogadható a webkamera megfelelő magasságának és szélességének felvételével. Ezután a téglalapot rajzoljuk a ROI paraméterek alapján, amelyeket fent definiáltunk. Ezután vágja ki a téglalapot, és töltse be a kód SWIFT detektor részébe.
Most a SIFT detektornak alapvetően két bemenete van, az egyik a kivágott kép, a másik pedig a képsablon, amelyet korábban definiáltunk, majd néhány egyezést ad nekünk, így az egyezések alapvetően az objektumok vagy kulcspontok száma, amelyek hasonlóak a kivágott képben és a célkép. Ezután meghatározzuk a mérkőzések küszöbértékét, ha az egyezés értéke meghaladja a küszöbértéket, akkor a képernyőn talált képet zöld színű ROI téglalap színnel tesszük.
Most térjünk vissza a kód fő részéhez, a funkcióhoz, amelyet SIFT detektornak hívnak. A bemenetet két képként veszi fel: az egyik kép az a kép, ahol az objektumot keresi, a másik pedig az az objektum, amelyhez megpróbálunk illeszteni hogy (képsablon). Ezután az első képet szürke színnel skálázza, és a képsablont határozza meg második képként. Ezután létrehozunk egy SIFT detektorobjektumot, és futtatjuk az OpenCV SIFT detektálás és kiszámítás funkciót a kulcspontok észleléséhez és a leírók kiszámításához, a leírók alapvetően azok a vektorok, amelyek tárolják a kulcspontokra vonatkozó információkat, és nagyon fontos, mivel az egyeztetést végezzük a képek leírói között.
Ezután határozza meg a FLANN alapú párosítót, nem foglalkozunk a mögötte lévő illesztés matematikai elméletével, de könnyen guglizhat róla. Először definiálja a kdtree indexet nullára, majd az indexet és a keresési paramétereket szótár formátumban állítjuk be, csak meghatározzuk a használni kívánt algoritmust, amely a KDTREE, és a használni kívánt fák számát, annál több fa minél bonyolultabbá válik és lassabb. És a keresési paraméterben adja meg az ellenőrzések számát, ami alapvetően a befejezendő mérkőzések száma.
Ezután hozza létre a FLANN alapú illesztőobjektumot az általunk korábban definiált paraméter betöltésével, amelyek indexparaméterek és keresési paraméterek, és ennek alapján hozza létre a FLANN alapú illesztőprogramunkat, amely egy KNN illesztő, ahol a KNN a K-legközelebbi szomszédok, alapvetően ez egy olyan módszer, ahol megkeressük a legközelebbi illesztőket és leírókat, és elvégezzük az illesztést a k inicializálási állandóval. Ez a FLANN alapú páros visszatér a megszerzett mérkőzések számához.
A FLANN alapú illesztés csak egy közelítés, így a FLANN alapú illesztõ pontosságának növelése érdekében elvégezzük a Lowe aránytesztjét, és mit csinál, az a knn flann alapú illesztõbõl keresi a találatokat és meghatároz néhány mátrix paramétert, amely itt távolság, amelynél a távolság numerikus függvény, és amint megfelel a kritériumoknak, csatolja a meccseket a jó mérkőzésekhez, és visszaadja a talált megfelelő találatokat, és így az élő videofolyam megmondja a képernyő sarkában talált mérkőzések számát.
Most nézzük meg a fenti leírás kódját:
import cv2 import numpy as np def sift_detector (new_image, image_template): # Funkció, amely összehasonlítja a bemeneti képet a sablonnal # Ezután visszaadja a közöttük lévő SIFT egyezések számát image1 = cv2.cvtColor (new_image, cv2.COLOR_BGR2GRAY) image2 = image_template # Create SIFT detektorobjektum #sift = cv2.SIFT () sift = cv2.xfeatures2d.SIFT_create () # A kulcspontokat és leírásokat a SIFT kulcspontok_1, leírók_1 = sift.detectAndCompute (kép1, Semmi) kulcspontok_2, leírók2, leíró_2 Nincs) # Határozza meg a Flann Matcher paramétereit. FLANN_INDEX_KDTREE = 0 index_params = dict (algoritmus = FLANN_INDEX_KDTREE, fák = 3) search_params = dict (ellenőrzés = 100) # Create a Flann Matcher tárgy Flann = cv2.FlannBasedMatcher (index_params, search_params) # Szerezze mérkőzést felhasználásával k legközelebbi szomszéd módszer # eredménye „matchs” a számos hasonló találat volt a két kép mérkőzések = flann.knnMatch (descriptors_1, descriptors_2, k = 2) # Tárolja a jó egyezéseket Lowe arány teszt segítségével: good_matches = m, n esetén: ha m.távolság <0,7 * n.távolság: good_matches.append (m) return len (good_matches) cap = cv2.VideoCapture (0) # Töltse be a képsablonunkat, ez a referencia képünk image_template = cv2.imread ('phone.jpg', 0), míg True: # Webkamera képek letöltése ret, frame = cap.read () # A webkamera keretmagasságának és szélességének lekérdezése, szélesség = frame.shape # A ROI mező méretének meghatározása top_left_x = int (width / 3) top_left_y = int ((height / 2) + (height / 4)) bottom_right_x = int ((width / 3) * 2) bottom_right_y = int ((magasság / 2) - (magasság / 4)) # Rajzoljon téglalap alakú ablakot az érdeklődési területünkhöz cv2. Téglalap (frame, (top_left_x, top_left_y), (bottom_right_x, bottom_right_y), 255, 3) # A fent definiált megfigyelés vágási ablaka levágva = frame # Flip keret tájolása vízszintesen frame = cv2.flip (frame, 1) # A SIFT egyezések számának lekérése = sift_detector (levágva, image_template) # Megjeleníti az aktuális sz. mérkőzések cv2.putText (frame, str (mérkőzések), (450,450), cv2.FONT_HERSHEY_COMPLEX, 2, (0,255,0), 1) # Küszöbértékünk az objektum detektálásának jelzésére # 10-et használunk, mivel a SIFT detektor kevés hamis pozitivitást ad vissza küszöb = 10 # Ha az egyezések meghaladják a küszöbértékünket, akkor az objektumot észleltük, ha az egyezés> küszöbérték: cv2.téglalap (keret, (felső_balold_x, felső_balold_y), (alsó_jobb_x, alsó_jobb_y), (0,255,0), 3) cv2.putText (keret, 'Object Found', (50,50), cv2.FONT_HERSHEY_COMPLEX, 2, (0,255,0), 2) cv2.imshow ('Object Detector using SIFT', frame) if cv2.waitKey (1) == 13: # 13 az Enter Key break cap.release () cv2.destroyAllWindows ()
Tárgyfelismerés ORB segítségével
Az objektumfelismerés a SIFT segítségével nagyon jó és pontos, mivel a kulcspontok alapján sok pontos egyezést generál, bár szabadalmaztatott, és ez megnehezíti a kereskedelmi alkalmazásokhoz való felhasználást, ennek másik kiútja az ORB algoritmus az objektum észleléséhez.
A SIFT által végzett objektum-észlelési módszerhez hasonlóan, amelyben a programot két részre osztottuk, itt is ugyanezt fogjuk követni.
Először meghatározzuk az ORB_detector függvényt, amely két bemenetet vesz igénybe: az egyik a webkameráról érkező élő közvetítés képe, a másik pedig az a képsablon, amely alapján a képünket össze akarjuk egyeztetni. Ezután szürkeárnyalatos webkameránk képét, majd inicializáljuk az ORB detektorunkat, és itt állítjuk be 1000 kulcspontra és az 1,2 méretezési paraméterekre. könnyedén eljátszhat ezekkel a paraméterekkel, majd észlelheti a képek kulcspontjait (kp) és leíróit (des), és a második paraméter, amelyet a DetectANDCompute funkcióban definiálunk, NINCS, kéri a képmaszk használatát vagy sem, és itt tagadjuk.
Ezután lépjen a detektorra, ahol korábban FLANN alapú illesztőt használtunk, de itt a BFMatcher-t fogjuk használni, a BFMatcher-en belül pedig két paramétert határozunk meg, az egyik a NORM_HAMMING, a másik pedig a crossCheck, amelynek értéke IGAZ.
Ezután számítsa ki a két kép közötti egyezéseket a fent definiált leírók használatával, ami összességében megadja az egyezések számát, mivel ezek az egyezések nem közelítőek, ezért nem kell elvégezni Lowe aránytesztjét, ehelyett a távolság alapján rendezzük a mérkőzéseket legkevésbé a távolság, minél jobb a meccs (itt a távolság a pontok közötti távolságot jelenti), és a végén a hosszfüggvény segítségével adjuk vissza a mérkőzések számát.
És a fő funkcióban a küszöböt sokkal magasabb értékre állítjuk, mivel a gömbdetektor nagy zajt generál.
Most nézzük meg az ORB alapú észlelés kódját
import cv2 import numpy as np def ORB_detector (new_image, image_template): # Funkció, amely összehasonlítja a bemeneti képet a sablonnal # Ezután visszaadja a közöttük lévő ORB egyezések számát image1 = cv2.cvtColor (new_image, cv2.COLOR_BGR2GRAY) # ORB detektor létrehozása 1000 kulcspont piramis faktorral 1,2 orb = cv2. ORB_create (1000, 1.2) # Az eredeti kép kulcspontjainak észlelése (kp1, des1) = orb.detectAndCompute (image1, None) # A forgatott kép kulcspontjainak észlelése (kp2, des2) = orb.detectAndCompute (image_template, None) # Matcher létrehozása # Megjegyzés: Már nem használunk Flannbased megfelelő bf = cv2.BFMatcher-t (cv2.NORM_HAMMING, crossCheck = True) # Végezzen egyezéseket = bf.match (des1, des2) # Rendezze a mérkőzéseket a távolság alapján. A legkevesebb # jobb egyezés = rendezve (mérkőzések, kulcs = lambda val: val.távolság) return len (mérkőzések) cap = cv2.VideoCapture (0) # Töltse be a képsablonunkat, ez a referencia képünk image_template = cv2.imread ('phone.jpg', 0) # image_template = cv2.imread (images / kitkat.jpg ', 0) , míg True: # Get webcam képek ret, frame = cap.read () # Get magassága és szélessége webkamera keret magassága, width = frame.shape # Meghatározza a ROI mező méreteit (ne feledje, hogy ezeknek a dolgoknak a hurkon kívül kell lennie) top_left_x = int (width / 3) top_left_y = int ((magasság / 2) + (magasság / 4)) alsó_jobb_x = int ((szélesség / 3) * 2) alsó_jobb_y = int ((magasság / 2) - (magasság / 4)) # Rajzoljon téglalap alakú ablakot érdeklődési terület cv2.téglalap (frame, (top_left_x, top_left_y), (bottom_right_x, bottom_right_y), 255, 3) # A fent definiált megfigyelési vágásablak levágva = frame # A keret tájolása vízszintesen frame = cv2.flip (frame, 1) # Az ORB találatok számának lekérdezése = ORB_detektor (levágva, image_template) # Az aktuális sz. a mérkőzések output_string = "Matches =" + str (egyezik) cv2.putText (frame, output_string, (50,450), cv2.FONT_HERSHEY_COMPLEX, 2, (250,0, 150), 2) # Az objektum detekciójának jelzésére vonatkozó küszöbérték # Új képek vagy megvilágítási feltételek esetén előfordulhat, hogy kísérletezni kell egy kicsit # megjegyzés: Az ORB detektor az első 1000 találat megszerzéséhez a 350 lényegében egy min. 35% -os egyezési küszöb = 250 # küszöbérték akkor objektumot észleltek, ha egyezik> küszöb: cv2.téglalap (keret, (felső_baloldali_x, felső_balold_y), (alsó_jobb_x, alsó_jobb_y), (0,255,0), 3) cv2.putText (keret, 'objektum megtalálva', (50), 50), cv2.FONT_HERSHEY_COMPLEX, 2, (0,255,0), 2) cv2.imshow ('ORB-t használó objektumdetektor', keret), ha a cv2.waitKey (1) == 13: # 13 az Enter Key break cap.release () cv2.destroyAllWindows ()
Orientált gradiensek hisztogramja
Most beszéljünk egy másik leíróról, amely az orientált színátmenetek hisztogramja (HOG).
A HOG-ok nagyjából klassz és hasznos leírók, és széles körben és sikeresen használják az objektumok detektálására, amint azt korábban láttuk, a képleírók, például a SIFT és az ORB, ahol ki kell számolnunk a kulcspontokat, majd le kell számolnunk a leírókat ezekből a kulcspontokból, a HOG-ok ezt a folyamatot eltérően. Az objektumokat egyetlen jellemzővektorként ábrázolja, szemben a jellemzővektorok halmazával, ahol mindegyik a kép egy szegmensét képviseli. Ez azt jelenti, hogy egyetlen vektoros tulajdonságunk van a teljes képhez.
A képet egy csúszó ablakdetektor számítja ki, ahol a HOG-leíró minden pozícióhoz kiszámításra kerül. Ezután minden pozíciót egyetlen jellemzővektorhoz egyesítenek.
A SIFT-hez hasonlóan a kép méretét is piramisozással állítják be.
Korábban olyan illesztőprogramokat használtunk, mint a FLANN és a BFMatcher, de a HOG-ok másképp csinálják az SVM (support vector machine) osztályozók segítségével, ahol minden kiszámított HOG-leírót egy SVM osztályozóhoz táplálnak, hogy megállapítsák, megtalálták-e az objektumot.
Itt található a Dalal & Triggs nagyszerű cikkére mutató link a HOG-ok emberi detektáláshoz történő felhasználásáról:
A orientált színátmenetek hisztogramja, lépésről lépésre:
A HOG megértése meglehetősen összetett lehet, de itt csak a HOG elméletével foglalkozunk anélkül, hogy elmélyülnénk a hozzá kapcsolódó matematikában.
Tehát ezt a képet vesszük kissé pixelezetté, a felső sarokban pedig 8x8 pixeles mező van itt, tehát ebben a mezőben kiszámoljuk az egyes pixelek gradiensvektorát vagy élének orientációit. Tehát ez azt jelenti, hogy ebben a mezőben kiszámítjuk a dobozban lévő pixelek képgradiens vektorát (ezek a kép intenzitásának egyfajta iránya vagy áramlása), és ez 64 (8 x 8) gradiensvektort generál, amelyeket ezután hisztogramként ábrázolnak. Képzeljünk el egy hisztogramot, amely az egyes gradiens vektorokat ábrázolja. Tehát, ha az összes pont vagy intenzitás egy irányban fekszik, akkor ennek az iránynak a hisztogramja mondjuk 45 fok, a hisztogram csúcsa 45 fokos lenne.
Tehát most azt tesszük, hogy minden cellát szögletes rekeszekre osztunk, ahol mindegyik bin egy gradiens iránynak felel meg (pl. X, y). A Dalal és Triggs papírban 9 szemetet használtak 0-180 ° -ig (20 ° -ig). Ez hatékonyan csökkenti a 64 vektort csak 9 értékre. Tehát amit tettünk, csökkentettük a méretét, de megtartottuk az összes szükséges információt.
A disznók kiszámításának következő lépése a normalizálás, normalizáljuk a színátmeneteket, hogy biztosítsuk az invarianciát a megvilágítás változásaira, azaz a fényerőre és a kontrasztra.
Ezen a képen az intenzitásértékek a négyzetben jelennek meg a megfelelő iránynak megfelelően, és mindegyikük 50-es különbséggel rendelkezik egymás között
∆ H = 50, ∆ v = 50; │∆│ = √50 2 +50 = 70,72, 70,72 / 100 = 0,707
A vektorokat elosztjuk a gradiens nagyságrendekkel, amit mindenkinek megkapunk 0,707, ez a normalizálás.
Hasonlóképpen, ha megváltoztatjuk az intenzitást vagy a kontrasztot, akkor az alábbi értékeket kapjuk.
∆ H = 50, ∆ v = 50; │∆│ = √50 2 +50 = 70,72, 70,72 / 100 = 0,707; ∆ H = 100, ∆ v = 100; │∆│ = √100 2 +100 = 141,42, 141,42 / 100 = 1,41
A normalizálás nem cellaszinten, hanem blokk szinten történik, tehát itt a blokkok alapvetően 4 cellából állnak, ez figyelembe veszi a szomszédos blokkokat, így normalizálódnak, miközben a kép nagyobb szegmenseit veszik figyelembe.
Most nézzük meg a kódot
import numpy as np import cv2 import matplotlib.pyplot as plt # Kép betöltése, majd szürkeárnyalatos image = cv2.imread ('elephant.jpg') szürke = cv2.cvtColor (image, cv2.COLOR_BGR2GRAY) # Eredeti kép megjelenítése cv2.imshow (' Input Image ', image) cv2.waitKey (0) #paraméterek, cellaméret és blokkméret meghatározása # hxw pixelekben cell_size = (8, 8) # hxw cellákban block_size = (2, 2) # tájolótartályok száma nbins = 9 # Az OpenCV HOG- leírójának használata # winSize a kép mérete a hog = cv2 cellaméret többszörösére vágva. HOGDescriptor (_winSize = (szürke.alakú // cella_méret * cella_méret, grey.shape // cell_size * cell_size), _blockSize = (block_size * cell_size, block_size * cell_size), _blockStride = (cell_size, cell_size), _cellSize = (cell_size, cell_size), _nbins = nbins) # Számos tömb alakot hozunk létre hog_features létrehozása n_cells = (szürke.alak // cella_méret, szürke.alak // cella_méret) # Először indexeljük a blokkokat. A # hog_feats mostantól tartalmazza az egyes irányok gradiens amplitúdóit, # a csoport minden egyes cellájához. Az indexelés sorok, majd oszlopok szerint történik. hog_feats = hog.compute (szürke).reshape (n_cells - block_size + 1, n_cells - block_size + 1, block_size, block_size, nbins).transpose ((1, 0, 2, 3, 4)) # Hozzon létre gradiens tömböt nbin dimenziókkal a színátmenetek orientációinak tárolásához gradiensek = np.zeros ((n_cellák, n_cellák, nbins)) # Hozzon létre dimenziótömböt cell_count = np.full ((n_cellák, n_cellák, 1), 0, dtype = int) # Blokk normalizálás off_y tartományban (block_size): off_x tartományban (block_size): gradiensek - block_size + off_y + 1, off_x: n_cells - block_size + off_x + 1] + = \ hog_feats cell_count - block_size + off_y + 1, off_x: n_cells - block_size + off_x + 1] + = 1 # Átlagos gradiens gradiens / = cell_count # HOG-ok ábrázolása a Matplotlib segítségével # szög 360 / nbins * irány color_bins = 5 plt.pcolor (gradiensek) plt.gca (). invert_yaxis () plt.gca (). set_aspect ('egyenlő', állítható = 'doboz') plt.colorbar () plt.show () cv2.destroyAllWindows ()
A kép azt mutatja, hogy az input kép hogyan jelenik meg HOG ábrázolásként.
HAAR kaszkád osztályozók
Amint azt korábban tárgyaltuk, kinyerhetjük a kép jellemzőit, és ezeket a szolgáltatásokat felhasználhatjuk az objektumok osztályozására vagy felderítésére.
Mik azok a HAAR kaszkád osztályozók?
Objektumdetektálási módszer, amely Haar jellemzőit beviszi egy osztályozó sorozatba (kaszkád), hogy azonosítsa a képen lévő objektumokat. Képzettek egy típusú objektum azonosítására, azonban többet is használhatunk párhuzamosan, pl.
HAAR osztályozók magyarázata:
A HAAR besorolókat rengeteg pozitív kép (azaz olyan képek, amelyeken jelen van a tárgy) és
negatív képeket (azaz képeket, amelyek nincsenek jelen tárgy nélkül) használják.
Miután megvan a kép, téglalap alakú blokkok csúszó ablakai segítségével vonjuk ki a funkciókat. Ezeket a jellemzőket (HAAR jellemzők) egyszerre értékelik, és úgy számítják ki, hogy a fehér téglalap alatti pixelintenzitások összegét kivonják a fekete téglalapokból.
Ez azonban nevetséges számú számítás, még egy 24 x 24 pixeles alapablak esetében is (180 000 generált funkció).
Tehát a kutatók kidolgozták az Integral Images nevű módszert, amely ezt négy tömbhivatkozással számolta ki. Azonban még mindig 180 000 funkcióval rendelkeztek, és többségük nem adott valódi értéket.
Fellendítése ezután meghatározásához használt a leginkább informatív jelleggel, Freund Schapire a Adaboost és azt állapította meg leginkább informatív funkciók a képet. A fokozás az a folyamat, amelynek során gyenge osztályozókat használunk erős osztályozók felépítéséhez, egyszerűen a súlytalan büntetések rendelésével a helytelen osztályozásokhoz. A 180 000 funkció 6000-re történő csökkentése, ami még mindig meglehetősen kevés funkció.
Ebben a 6000 szolgáltatásban egyesek informatívabbak lesznek, mint mások. Tehát ha a leginformatívabb funkciókat használtuk annak ellenőrzésére, hogy a régiónak lehet-e arca (a hamis pozitívumokkal nem lesz nagy baj). Ezzel feleslegessé teszi a 6000 jellemző egyszerre történő kiszámítását. Ezt a koncepciót a besorolók kaszkádjának nevezik - az arcfelismeréshez a Viola Jones módszer 38 szakaszt használt.
Arc- és szemérzékelés
Tehát miután elméleti ismereteket szereztünk a HAAR kaszkádokról, végre meg fogjuk valósítani azokat, hogy a dolgok nagyjából egyértelműek legyenek, részenként meg fogjuk bontani a leckéket, először a frontális arcot észleljük, majd a frontális arc észlelésére és végül a webkamerán keresztül észlelnénk az arcot és a szemet.
Tehát ehhez előképzett osztályozókat fogunk használni, amelyeket az OpenCV.xml fájlokként biztosított, az xml a kiterjeszthető jelölőnyelvet jelenti, ezt a nyelvet hatalmas mennyiségű adat tárolására használják, akár adatbázist is építhetne rá.
Ezen osztályozókhoz ezen a linken férhet hozzá .
Arcfelismerés
Próbáljuk meg a frontális arcfelismerést, itt érheti el a frontális arcérzékelő kaszkádját. Csak csomagolja ki a zip fájlt az xml fájl megszerzéséhez.
import numpy as np import cv2 # Osztjuk az OpenCV CascadeClassifier függvényét arra, ahová az # osztályozónkat (XML fájlformátum) tároljuk, ne felejtsük el, hogy a kódot és az osztályozót ugyanabban a mappában kell tartani: face_cascade = cv2.CascadeClassifier ('haarcascade_frontalface_default.xml') # Betöltés képünk ezt követően szürkeárnyalatos képpé alakítja = cv2.imread ('Trump.jpg') szürke = cv2.cvtColor (image, cv2.COLOR_BGR2GRAY) # Osztályozónk az észlelt arc ROI- ját adja vissza duplaként # A bal felső sarokban tárolja koordináta és a jobb alsó koordináták # visszaadja a listák listáját, amelyek a különböző észlelt arcok helyét jelentik. arcok = face_cascade.detectMultiScale (szürke, 1.3, 5) # Ha nincs felismert arcok, face_classifier visszatér, és az üres tuple ha arcok is (): print („Nem arcot talált”) # Mi halad végig arcunkat tömb és rajzoljon egy téglalapot # minden arc arcok az (x, y, w, h) arcokban: cv2.téglalap (kép, (x, y), (x + w, y + h), (127,0, 255), 2) cv2.imshow ('Arcfelismerés', kép) cv2.waitKey (0) cv2.destroyAllWindows ()
Most kombináljuk az arc- és szemérzékelést, ugyanabban a zip fájlban férhet hozzá a szemérzékelő kaszkádjához.
import numpy as np import cv2 face_classifier = cv2.CascadeClassifier ('haarcascade_frontalface_default.xml') eye_classifier = cv2.CascadeClassifier ('haarcascade_eye.xml') img = cv2.imread ('Trump.jpgc) im cv2.COLOR_BGR2GRAY) arcok = face_classifier.detectMultiScale (szürke, 1.3, 5) # Ha nem észleltek arcokat, akkor a face_classifier visszatér, és üres a duplája, ha az arcok (): print ("Nem található arc") (x, y, w, h) arcokban: cv2.téglalap (img, (x, y), (x + w, y + h), (127,0, 255), 2) cv2.imshow ('img', img) roi_gray = szürke roi_color = img szem = eye_classifier.detectMultiScale (roi_gray) cv2.waitKey (0) a (ex, ey, ew, eh) számára a szemekben: cv2.téglalap (roi_color, (ex, ey), (ex + ew, ey + eh), (255,255,0), 2) cv2.imshow ('img', img) cv2.waitKey (0) cv2.destroyAllWindows () cv2.waitKey (0)
Tehát ez a kód ugyanaz, mint, hogy a kódot az arcfelismerés, de itt van hozzá szeme vízesések és módon észleli őket, ahogy láthatjuk úgy döntöttünk, a szürke beosztott változata az arc, mint a paraméter a detectMultiScale számára a szemek, ami a számítás csökkenéséhez vezet, mivel a szemeket csak ezen a területen fogjuk csak észlelni.
Élő arc- és szemérzékelés
Tehát eddig arc- és szemfelismerést hajtottunk végre, most ugyanezt valósítsuk meg a webkameráról érkező élő videó közvetítéssel is. Ebben ugyanezt az arc és a szem érzékelését fogjuk megtenni, de ezúttal a webkamera élő közvetítéséért fogjuk megtenni. Az alkalmazás nagy részében az arcát kiemelte egy doboz körül, de itt valami mást tettünk, amellyel kivágottnak találta az arcát, és csak ebben azonosította a szemét.
Tehát itt importáljuk az arc és a szem osztályozóját, és meghatároztunk egy funkciót az arc és a szem észlelésének összes feldolgozásához. Ezután elindult a webkamera-adatfolyam, és meghívta az arcérzékelő funkciót az arc és a szem észleléséhez. Az a paraméter, amelyet az arcérzékelő funkción belül definiálunk, az élő webkamerából származó folyamatos képek
import CV2 import numpy mint np face_classifier = cv2.CascadeClassifier (haarcascade_frontalface_default.xml) eye_classifier = cv2.CascadeClassifier (haarcascade_eye.xml ') def face_detector (img, méret = 0,5): # Convert kép szürkeárnyalatossá szürke = cv2.cvtColor (img, cv2.COLOR_BGR2GRAY) arcok = face_classifier.detectMultiScale (szürke, 1.3, 5), ha az arcok értéke (): az img értéket adja vissza az (x, y, w, h) arcokra: x = x - 50 w = w + 50 y = y - 50 h = h + 50 cv2.négyszög (img, (x, y), (x + w, y + h), (255,0,0), 2) roi_gray = szürke roi_color = img szem = eye_classifier.detectMultiScale (roi_gray) a (ex, ey, ew, eh) szemekben: cv2.téglalap (roi_color, (ex, ey), (ex + ew, ey + eh), (0,0,255), 2) roi_color = cv2.flip (roi_color, 1) visszatér roi_color cap = cv2.VideoCapture (0) míg True: ret, frame = cap.read () cv2.imshow ('Arcfelszívónk', face_detector (keret)), ha cv2.waitKey (1) == 13: # 13 az Enter Key break cap.release () cv2.destroyAllWindows ()
Kaszkád osztályozók beállítása
A detektorMultiScale-ben megadott paraméterek, a bemeneti képen kívül, a következő jelentőséggel bírnak
mi osztályozó. DetectMultiScale (bemeneti kép, skála tényező, minimális szomszédok)
- Méretfaktor Megadja, hogy mennyit csökkentünk a képméretből minden egyes méretezéskor. Például az arcfelismerésben általában az 1.3-at használjuk. Ez azt jelenti, hogy 30% -kal kicsinyítjük a képet minden méretezéskor. A kisebb értékek, például az 1.05 kiszámítása hosszabb időt vesz igénybe, de növeli az észlelés sebességét.
- Min szomszédok Megadja az egyes potenciális ablakok szomszédainak számát, hogy pozitív észlelésnek lehessen tekinteni. Általában 3-6. Érzékenységi beállításként működik, az alacsony értékek néha többszörös arcokat érzékelnek egyetlen arc felett. A magas értékek kevesebb hamis pozitív eredményt biztosítanak, de hiányozhat néhány arc.
Autók és gyalogosok észlelése videókban
Most a gyalogosokat és az autókat fogjuk észlelni a videókban a HAAR kaszkádokkal, de abban az esetben, ha nem töltődik be videó, és a kód hibátlanul fordít, akkor a következő lépéseket kell végrehajtania:
Ha a kód futtatása után nem töltődik be videó, akkor előfordulhat, hogy át kell másolnia az opencv_ffmpeg.dl fájlt a : opencv \ sources \ 3rdparty \ ffmpeg fájlból, hogy beillessze a python telepített helyére, pl. C: \ Anaconda2
Miután ez másolt akkor kell átnevezni a fájlt a változattól függően a OpenCV te using.eg ha használja OpenCV 2.4.13 majd nevezze át a fájlt: opencv_ffmpeg2413_64.dll vagy opencv_ffmpeg2413.dll (ha X86-os gépet használva) opencv_ffmpeg310_64.dll vagy opencv_ffmpeg310.dll (ha X86-os gépet használ)
A python.exe telepítési helyének megismeréséhez csak futtassa ezt a két kódsort, és kinyomtatja a python telepítésének helyét.
sys nyomtatás importálása (sys.exe)
Most, ha ezeket a lépéseket sikeresen végrehajtotta, lépjünk a gyalogosok észleléséhez szükséges kódra
Megadhatja a kaszkádot a gyalogosok észleléséhez és az itt csatolt zip fájlból.
import cv2 import numpy as np # Hozza létre testosztályozónkat body_classifier = cv2.CascadeClassifier ('haarcascade_fullbody.xml') # Videofájl rögzítésének kezdeményezése, itt azt a videofájlt használjuk, amelyben a gyalogosokat észleljük cap = cv2.VideoCapture ('walking.avi') # Hajtsa végre a videó sikeres betöltését, míg a cap.isOpened (): # A videó egyes képkockáinak olvasása ret, frame = cap.read () # itt átméretezzük a keretet annak méretének felére, azért tesszük, hogy felgyorsítsuk a # besorolást, mivel a nagyobb képeken sokkal több ablakon lehet átcsúszni, ezért összességében csökkentjük a felbontást A videó # felére annyit mutat, mint amit 0.5 jelez, és gyorsabb interpolációs módszert is használunk, amely a # interlinear frame = cv2.resize (frame, None, fx = 0.5, fy = 0.5, interpolation = cv2.INTER_LINEAR) szürke = cv2. cvtColor (frame, cv2.COLOR_BGR2GRAY) # Keret átadása testosztályozó testeinknek = body_classifier.detectMultiScale (szürke, 1.2, 3) # Kivonat határoló dobozokat bármely (x, y, w, h) számára azonosított testhez a testekben: cv2. téglalap (keret, (x, y), (x + w, y + h), (0, 255, 255), 2) cv2.imshow ('Gyalogosok', keret), ha cv2.waitKey (1) == 13: # 13 az Enter Key break cap.release () cv2.destroyAllWindows ()
Miután sikeresen észleltük a gyalogosokat a videóban, térjünk át az autó észlelés kódjára. Innen megkaphatja a gyalogosok észlelésének kaszkádját.
import cv2 import time import numpy as np # Test-osztályozó létrehozása car_classifier = cv2.CascadeClassifier ('haarcascade_car.xml') # Videofájl-beindítás kezdeményezése a cap fájlhoz = cv2.VideoCapture ('cars.avi') # Hajtsa végre, ha a videó sikeres betöltve, amíg cap.isOpened (): time.sleep (.05) # Olvassa el az első képkockát ret, frame = sapka.read () szürke = cv2.cvtColor (keret, cv2.COLOR_BGR2GRAY) # Keretet adjon át autós osztályozónknak autók = car_classifier.detectMultiScale (szürke, 1.4, 2) # Húzza ki a határoló dobozokat az (x, y, w, h) számára azonosított testekhez az autókban: cv2.rectangle (frame, (x, y), (x + w, y + h), (0, 255, 255), 2) cv2.imshow ('Cars', frame) if cv2.waitKey (1) == 13: # 13 az Enter Key break cap.release () cv2.destroyAllWindows ()
Észrevette, hogy hozzáadtuk az time.sleep (.05) értéket , ez csak késleltetett képkockasebesség, így megerősítheti, hogy az összes autó helyesen van-e azonosítva, vagy egyszerűen eltávolíthatja, ha hozzáad egy megjegyzés címkét.
Ezt a cikket a Master Computer Vision ™ OpenCV4 Python-ban, az Udemy-re vonatkozó mélytanulási tanfolyammal készítették, Rajeev Ratan készítette. Iratkozzon fel rá, hogy többet tudjon meg a Computer Vision-ről és a Pythonról.