介绍
在本文中,我们将讨论在 OpenCV python 中使用 Haar Cascade(级联)实现人脸检测器。
(资料图片)
识别图像中的给定对象称为对象检测。可以使用多种技术来完成此任务,但在本文中,我们将使用带有预训练 XML 文件的 haar 级联。这是执行对象检测的最简单方法。
Haar 级联已用于低边缘设备上的对象检测,它是 OpenCV 中最流行的对象检测算法之一。
Haar 级联计算量不大;因此它适用于计算能力较小的小型设备。
Haar 级联
什么是 Haar 级联,它是如何工作的?
Haar 级联 是一种基于特征的对象检测算法,用于从图像中检测对象。Cascade 函数在大量正负图像上进行训练以进行检测。
该算法不需要大量计算并且可以实时运行。我们可以为动物、汽车、自行车等自定义对象训练自己的级联函数。
Haar 级联 不能用于人脸识别,因为它只能识别匹配的形状和大小。
Haar 级联使用 Cascade 函数和 Cascade 窗口。它尝试计算每个窗口的特征并进行正负分类。如果窗口可以是对象的一部分,则为正,否则为负。
Haar 级联可以理解为二进制分类器。它为那些可以成为我们对象一部分的级联窗口指定正值,为那些不能成为我们对象的一部分的窗口指定负值。
· Haar 级联可以实时工作。
· 与现代对象检测算法相比,Haar 级联并不准确。
· 它检测到许多误报。这可以在一定程度上进行调整,但不能完全删除。
· 实现起来非常简单。
· Haar 级联最大的缺点是它的误报检测。
预训练的 Haar 级联
有许多预训练的 haar 级联文件使实施变得超级容易。我们也可以训练自己的 haar 级联,但这需要大数据进行训练。
OpenCV 库在 GitHub 上管理所有流行的 haar 级联预训练文件的存储库
这些文件可用于各种对象检测任务,例如:
· 人脸检测
· 眼睛检测
· 车辆检测
· 鼻子/嘴巴检测
· 身体检测
· 车牌检测
Haar 级联将其特征存储在一个 XML 文件中;这些文件可以直接加载到 OpenCV 中,使用 Haar 级联进行对象检测。
在 OpenCV 中实现 Haar 级联
如果你正在使用 OpenCV 提供的存储库中可用的任何预训练对象检测,则只需下载预训练的 XML 文件。
在 Python 中安装 OpenCV
可以使用 python 中的 pip 包管理器安装 OpenCV。
!pip install opencv-python
#---OR ---
!pip install opencv-contrib-python
在 OpenCV 中加载 Haar 级联
我们可以使用函数cv2.CascadeClassifier加载 haar-cascade XML 文件。
face_detector=cv2.CascadeClassifier(‘haarcascade_frontalface_default.xml’)
eye_dectector = cv2.CascadeClassifier(‘haarcascade_eye.xml’)
一旦加载了 XML 文件,我们就可以调用检测器函数。
results = face_detector.detectMultiScale(gray_img, scaleFactor=1.15,minNeighbors=5,minSize=(34, 35), flags=cv2.CASCADE_SCALE_IMAGE)
# import the necessary packages
import cv2
face_detector=cv2.CascadeClassifier('haarcascade_frontalface_default.xml')
eye_dectector = cv2.CascadeClassifier('haarcascade_eye.xml')
image = cv2.imread('tomato.jpg')
gray_img = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
results = face_detector.detectMultiScale(gray_img, scaleFactor=1.15,minNeighbors=5,minSize=(34, 35), flags=cv2.CASCADE_SCALE_IMAGE)
print(results)
results是检测到的对象周围的边界框坐标 (x,y,w,h) 的列表。
detectMultiScale中的参数:
· scaleFactor:这表示对象的大小与原始图像相比减小了多少。
· minNeighbors:此参数告诉在单个边界框中应该有多少个邻居。
· minSize :这表示我们图像中对象的最小可能大小。如果我们的对象小于 minSize ,它将被忽略。
注意:对于对象检测,我们必须使用gray_image, minNeighbors,scaleFactor等参数。
人脸检测
让我们以第一个使用预训练 haar 级联的对象检测示例为例,我们将使用 Python 从图片中检测人脸。
import numpy as np
import cv2
#---loading the Haar 级联 detector using CascadeClassifier---face_detector=cv2.CascadeClassifier('haarcascade_frontalface_default.xml')
#---Loading the image from local -----
img = cv2.imread('team_india.jpg')
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
results = face_detector.detectMultiScale(gray, 1.3, 5)
for (x,y,w,h) in results:
cv2.rectangle(img,(x,y),(x+w,y+h),(0,255,0),2)
cv2.imshow('img',img)
cv2.waitKey(0)
cv2.destroyAllWindows()
· results它包含图片中边界框的坐标。
· detectMultiScale此方法仅适用于灰度图片。
· cv2.rectangle允许我们在传递坐标后绘制矩形。
· scaleFactor = 1.3FineTuning 参数,取值范围从 1 到 2。
分级检测
Haarcascade 支持分级检测,这意味着 Haar 级联能够以分级方式检测单个帧内的多个对象。
假设我们必须检测人类的面部和眼睛。要继续执行任务,我们需要执行以下步骤。
· 检测人脸
· 对于每张脸,裁剪人脸并将其转发以进行眼睛检测
· 在找到眼睛的坐标 ( ex,ey,ew,eh) 后,在原始图片中的眼睛周围绘制一个边界框。
· 在原始图片上使用坐标(x,y,w,h)在面部周围绘制一个边界框。
import numpy as np
import cv2
face_detector1=cv2.CascadeClassifier('haarcascade_frontalface_default.xml')
eye_detector1 = cv2.CascadeClassifier('haarcascade_eye.xml')
img = cv2.imread('uman.jpg')
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
faces_result = face_detector.detectMultiScale(gray, 1.3, 5)
for (x,y,w,h) in faces_result:
img = cv2.rectangle(img,(x,y),(x+w,y+h),(255,0,0),2)
roi_gray = gray[y:y+h, x:x+w]
roi_color = img[y:y+h, x:x+w]
eyes = eye_detector.detectMultiScale(roi_gray)
for (ex,ey,ew,eh) in eyes:
cv2.rectangle(roi_color,(ex,ey),(ex+ew,ey+eh),(0,255,0),2)
cv2.imshow('img',img)
cv2.waitKey(0)
cv2.destroyAllWindows()
实时实现人脸检测
我们可以在 OpenCV 视频流中使用 Haar 级联进行对象检测,只需要在 OpenCV 中读取视频或摄像头,其余的都是一样的。
视频源是一系列帧,因此代码与单个帧相同。由于其轻计算要求,Haar 级联每秒运行良好。
我们将读取 OpenCV 视频摄像头输入以实时拍摄图像。
import cv2
face_detector1 = cv2.CascadeClassifier('haarcascade_frontalface_default.xml')
eye_dectector1 = cv2.CascadeClassifier('haarcascade_eye.xml')
# reading the input image now
cap = cv2.VideoCapture(0)
while cap.isOpened():
_, frame = cap.read()
gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
faces = face_detector1.detectMultiScale(gray,1.1, 4 )
for (x,y, w, h) in faces:
cv2.rectangle(frame, pt1 = (x,y),pt2 = (x+w, y+h), color = (255,0,0),thickness = 3)
roi_gray = gray[y:y+h,x:x+w]
roi_color = frame[y:y+h, x:x+w]
eyes = eye_dectector1.detectMultiScale(roi_gray)
for (ex,ey, ew, eh) in eyes:
cv2.rectangle(roi_color, (ex,ey), (ex+ew, ey+eh), (0,255,0), 5)
cv2.imshow("window", frame)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
frame.release()
眼睛和面部的边界框将是实时的,并且每帧都会发生变化。
Haar 级联人脸检测的局限性
Haar 级联对于人脸、汽车等一些对象仍然很受欢迎,这些对象很容易区分。
Haar 级联不能用于深度目标检测,如谷物类型等。
Haar 级联算法有一些限制:
· 与现代对象检测器相比,精度较低。
· 高假阳性检测。
· 需要手动调整参数。
· 为自定义对象训练 haar 级联并不容易。
结论
在本文中,我们讨论了 haar 级联的工作原理以及如何在 python 中使用 OpenCV实现 haar 级联以进行对象检测。我们使用预训练的 haar 级联文件进行人脸检测和眼睛检测,然后我们实时执行相同的操作。
我们还谈到了 haar 级联算法的局限性,为什么它仍然被广泛使用,为什么它这么快。
· 可以使用手动参数调整来修复误报率。
· YOLO、SSD 和其他深度学习对象检测算法保证了更高的准确性。
· 训练自定义 haar 级联既耗时又低效。