TShopping

 找回密碼
 註冊
搜索
查看: 1424|回復: 0
打印 上一主題 下一主題

[教學] Python 利用 OpenCV抓取相片中的臉部數據

[複製鏈接]
跳轉到指定樓層
1#
發表於 2021-11-23 22:52:45 | 只看該作者 |只看大圖 回帖獎勵 |倒序瀏覽 |閱讀模式
 
Push to Facebook
為了將圖片數據轉換為適合 AI訓練的格式,利用 OpenCV先對臉部進行辨識,然後將臉部數據另存為統一的格式。
  1. import cv2

  2. face_cascade = cv2.CascadeClassifier('./cascades/haarcascade_frontalface_default.xml')
  3. eye_cascade = cv2.CascadeClassifier('./cascades/haarcascade_eye.xml')

  4. def detect(filename):
  5.     img = cv2.imread(filename)
  6.     gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
  7.     faces = face_cascade.detectMultiScale(gray,
  8.                                           scaleFactor=1.2,
  9.                                           minNeighbors=3,)
  10.     for (x,y,w,h) in faces:
  11.         roi_gray = gray[y:y+h, x:x+w]
  12.         eyes = eye_cascade.detectMultiScale(roi_gray,
  13.                                             scaleFactor=1.02,
  14.                                             minNeighbors=3,
  15.                                             minSize=(40,40),)
  16.         img = cv2.rectangle(img,(x,y),(x+w,y+h),(255,0,0),2)
  17.         for (ex,ey,ew,eh) in eyes:
  18.             img = cv2.rectangle(img,(x+ex,y+ey),(x+ex+ew,y+ey+eh),(0,255,0),2)
  19.     cv2.imwrite('./tzuyu_face.jpg', img)

  20. detect('tzuyu.jpg')
複製代碼

利用 cv2.CascadeClassifier導入辨識工具,其中選擇了臉部和眼睛的辨識工具。
讀取圖像數據後,轉為灰階,利用detectMultiScale做臉部和眼睛的辨識。
detectMultiScale中的數據參數分別是
  • 圖片數據
  • ScaleFactor:每次搜尋方塊減少的比例
  • minNeighbers:每個目標至少檢測到幾次以上,才可被認定是真數據。
  • minSize:設定數據搜尋的最小尺寸 ,如 minSize=(40,40)

利用 cv2.rectangle把辨識到的臉部或眼睛進行標注,參數依序是
  • 圖片數據
  • 兩個對角座標
  • 線的顏色
  • 線的粗細

第一個迴圈中先利用以辨識的臉部再進行眼睛的辨識。
其中 Haar級聯數據可以從這裡下載。裡面提供了各類辨識的工具。
另外也可以使用 LBP級聯數據,可以從這裡下載。

先試看看子瑜女神,有沒有辦法被辨識。

子瑜女神看來起來辨識滿成功的。
接著看看失敗的例子,用了同樣的參數辨識一下 Twice和愉快伙伴們?


看來挺失敗的,娜璉和其中兩位愉快伙伴完全沒有辨識出臉,眼睛的部份大多都沒有辨識成功。為了辨識成功,可能需要調整一下參數。至於如何避免 OpenCV混淆眼睛和嘴,本人目前沒有對策,求高手指點。不過還好團體照不是我要辨識的主要目標。
接著修改 detect,把辨識出的臉,另存為供 AI訓練的圖像。

  1. import cv2

  2. face_cascade = cv2.CascadeClassifier('./cascades/haarcascade_frontalface_default.xml')
  3. eye_cascade = cv2.CascadeClassifier('./cascades/haarcascade_eye.xml')

  4. face_filename = 1
  5. def detect(filename):
  6.     img = cv2.imread(filename)
  7.     gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
  8.     faces = face_cascade.detectMultiScale(gray,
  9.                                           scaleFactor=1.2,
  10.                                           minNeighbors=3,)
  11.     for (x,y,w,h) in faces:
  12.         roi_gray = gray[y:y+h, x:x+w]
  13.         eyes = eye_cascade.detectMultiScale(roi_gray,
  14.                                             scaleFactor=1.02,
  15.                                             minNeighbors=3,)
  16.         if len(eyes)>=2:
  17.             f = cv2.resize(gray[y:y+h, x:x+w], (200, 200))
  18.             global face_filename
  19.             name = './face/%d.png' % face_filename
  20.             cv2.imwrite(name, f)
  21.             face_filename += 1
  22.         else:
  23.             pass
  24.     print('Working with %s' % filename)
複製代碼
對臉部和眼睛進行辨識,至少辨識出兩隻眼睛(無論對錯)才進行儲存,輸出為 200x200的 png格式。
我沒有設定minSize,因為我的數據有點少解析度落差也很大,所以不想要太嚴格。
  1. import os

  2. img_list = []
  3. for fileNames in os.walk("."):
  4.     filename_extension = ['.jpg', '.png', '.jpeg', '.JPG', '.gif']
  5.     for fe in filename_extension:
  6.         for fileName in fileNames[-1]:
  7.             if fileName.endswith(fe):
  8.                 img_list.append(fileName)

  9. for img in img_list:
  10.     detect(img)
複製代碼

做法可能沒有很聰明,利用 os.walk把該資料夾中的各種格式的圖像名稱儲存成 list,再利用迴圈對圖像一個個辨識。
無論原圖解析度如何,全都會輸出統一的格式,輸出的圖像如下。


文章出處


 

臉書網友討論
*滑块验证:
您需要登錄後才可以回帖 登錄 | 註冊 |

本版積分規則



Archiver|手機版|小黑屋|免責聲明|TShopping

GMT+8, 2024-4-25 00:06 , Processed in 0.076420 second(s), 25 queries .

本論壇言論純屬發表者個人意見,與 TShopping綜合論壇 立場無關 如有意見侵犯了您的權益 請寫信聯絡我們。

Powered by Discuz! X3.2

© 2001-2013 Comsenz Inc.

快速回復 返回頂部 返回列表