【人脸识别(五)】:基于Haar+Adaboost的人脸检测算法,及实例教程_ ...

【人脸识别(五)】:基于Haar+Adaboost的人脸检测算法,及实例教程_ ...

2023年8月2日发(作者:)

【⼈脸识别(五)】:基于Haar+Adaboost的⼈脸检测算法,及实例教程

⽬录看了很多的⽂章,认为和对adaboost算法讲解的⽐较详细,查阅相关资料后,本⽂将介绍haar+adaboost算法理论和具体实现,多处参考以上两位博主。1. adaboost由来adaboost⽅法是Boosting⽅法的提升版,Boosting⽅法⼜起源于PCA学习模型。1984年Valiant提出PCA模型,1990年,SChapire就⾸先构造出⼀种多项式级的算法,将弱学习算法提升为强学习算法,就是最初的Boosting算法。1993年,Drucker和Schapire⾸次以神经⽹络作为弱学习器,利⽤Boosting算法解决实际问题。1994年,Kearns和Valiant证明,在Valiant的PAC(Probably ApproximatelyCorrect)模型中,只要数据⾜够多,就可以将弱学习算法通过集成的⽅式提⾼到任意精度。1995年,Freund在Kearns和Valiant证明的基础上提出了⼀种效率更⾼的Boosting算法,即现在的Adaboost模型,对Boosting算法有巨⼤提升。PCA(Probably Approximately Correct)模型是计算学习理论中常⽤的模型,PAC学习的实质就是在样本训练的基础上,使算法的输出以概率接近未知的⽬标概念。PAC学习模型是考虑样本复杂度(指学习器收敛到成功假设时⾄少所需的训练样本数)及计算复杂度(指学习器收敛到成功假设时所需的计算量)的⼀个基本框架,成功的学习被定义为形式化的概率理论。Boosting 原意为提升、加强,现在⼀般指的是将弱学习算法提升为强学习算法的⼀类算法。boosting模型就是学习⼀系列的分类器,每个分类器对其前⼀个分类器产⽣的错误给予更⼤的重视,并增加导致错误分类的样本权值,重新对该样本训练分类器后,再学习下⼀个分类器。该训练过程重复到设定的次数后停⽌,最终分类器从这⼀系列的分类器中得出。Boosting是⼀种把若⼲个若分类器结合到⼀个强分类器中,从⽽⼤⼤提⾼检测性能的⽅法。强分类器对数据进⾏分类,是通过弱分类器的多数投票机制进⾏的。Adaboost(Adaptive Boosting)是Boosting家族的代表算法之⼀,不需要任何关于弱学习器性能的先验知识,⽽且和Boosting算法具有同样的效率,所以在提出之后得到了⼴泛的应⽤。Adaboost算法已被证明是⼀种有效⽽实⽤的Boosting算法,其算法原理是通过调整样本权重和弱分类器权值,从训练出的弱分类器中筛选出权值系数最⼩的弱分类器组合成⼀个最终强分类器。基于训练集训练弱分类器,每次下⼀个弱分类器都是在样本的不同权值集上训练获得的。每个样本被分类的难易度决定权重,⽽分类的难易度是经过前⾯步骤中的分类器的输出估计得到的。Adaboost算法在样本训练集使⽤过程中,对其中的关键分类特征集进⾏多次挑选,逐步训练分量弱分类器,⽤适当的阈值选择最佳弱分类器,最后将每次迭代训练选出的最佳弱分类器构建为强分类器。其中,级联分类器的设计模式为在尽量保证感兴趣图像输出率的同时,减少⾮感兴趣图像的输出率,随着迭代次数不断增加,所有的⾮感兴趣图像样本都不能通过,⽽感兴趣样本始终保持尽可能通过为⽌。⾸先需要了解若分类器、强分类器和级联分类器。弱分类器:没有专门的定义,可以理解为对分类的效果较弱,正确率较低。强分类器:即分类学习正确率较⾼,有显著的分类分类效果。级联分类器:将多个分类器连在⼀起组成⼀个强分类器,再由多个强分类器级联在⼀起组成⼀个标准分类器。Adaboost是⼀种基于级联分类模型的分类器,级联分类模型可以⽤下图表⽰:所有样本进⼊第⼀个强分类器,若为正例则进⼊下⼀个强分类器,否则,直接作为负例输出,以此类推,直到最后的强分类器输出正例,作为最终的输出结果。有些强分类器可能包含10个弱分类器,有些则包含20个弱分类器,⼀般情况下⼀个级联⽤的强分类器包含20个左右的弱分类器,然后在将10个强分类器级联起来,就构成了⼀个级联强分类器,这个级联强分类器中总共包括200弱分类器。因为每⼀个强分类器对负样本的判别准确度⾮常⾼,所以⼀旦发现检测到的⽬标位负样本,就不在继续调⽤下⾯的强分类器,减少了很多的检测时间。因为⼀幅图像中待检测的区域很多都是负样本,这样由级联分类器在分类器的初期就抛弃了很多负样本的复杂检测,所以级联分类器的速度是⾮常快的;只有正样本才会送到下⼀个强分类器进⾏再次检验,这样就保证了最后输出的正样本的伪正(false positive)的可能性⾮常低。级联结构分类器由多个弱分类器组成,每⼀级都⽐前⼀级复杂。每个分类器可以让⼏乎所有的正例通过,同时滤除⼤部分负例。这样每⼀级的待检测正例就⽐前⼀级少,排除了⼤量的⾮检测⽬标,可⼤⼤提⾼检测速度。其次,Adaboost是⼀种迭代算法。初始时,所有训练样本的权重都被设为,在此样本分布下训练出⼀个弱分类器。在第(,T为迭代次数)次迭代中,样本的权重由第n-1次迭代的结果⽽定。在每次迭代的最后,都有⼀个调整权重的过程,被分类错误的样本将得到更⾼的权重。这样分错的样本就被突出出来,得到⼀个新的样本分布。在新的样本分布下,再次对弱分类器进⾏训练,得到下⼀个新的弱分类器。经过T次循环,得到T个弱分类器,把这T个弱分类器按照⼀定的权重叠加起来,就得到最终的强分类器。Aadboost 算法系统具有较⾼的检测速率,且不易出现过适应现象。但是该算法在实现过程中为取得更⾼的检测精度则需要较⼤的训练样本集,在每次迭代过程中,训练⼀个弱分类器则对应该样本集中的每⼀个样本,每个样本具有很多特征,因此从庞⼤的特征中训练得到最优弱分类器的计算量增⼤。2. Haar特征Harr-like特征是Viola等提出的⼀种简单矩形特征,因其类似于Harr⼩波⽽得名,它反映了图像局部的灰度化。影响AdaBoost检测训练算法速度很重要的两⽅⾯是特征的选取和特征值的计算。脸部的⼀些特征可以由矩形特征(特征模板)简单地描绘。如下图⽰范:上图中两个矩形特征,表⽰出⼈脸的某些特征。⽐如中间⼀幅表⽰眼睛区域的颜⾊⽐脸颊区域的颜⾊深,右边⼀幅表⽰⿐梁两侧⽐⿐梁的颜⾊要深。同样,其他⽬标,如眼睛等,也可以⽤⼀些矩形特征来表⽰。在给定有限的数据情况下,基于特征的检测能够编码特定区域的状态,⽽且基于特征的系统⽐基于像素的系统要快得多。矩形特征对⼀些简单的图形结构,⽐如边缘、线段,⽐较敏感,但是其只能描述特定⾛向(⽔平、垂直、对⾓)的结构,因此⽐较粗略。如上图,脸部⼀些特征能够由矩形特征简单地描绘,例如,通常眼睛要⽐脸颊颜⾊更深;⿐梁两侧要⽐⿐梁颜⾊要深;嘴巴要⽐周围颜⾊更深。对于⼀个 24×24 检测器,其内的矩形模板决定的矩形特征数量超过160,000个,必须通过特定算法甄选合适的矩形特征,并将其组合成强分类器才能检测⼈脸。常⽤的矩形特征有三种:两矩形特征、三矩形特征、四矩形特征,如图:由图表可以看出,两矩形特征反映的是边缘特征,三矩形特征反映的是线性特征、四矩形特征反映的是特定⽅向特征。LienhartR.等对Haar-like矩形特征库作了进⼀步扩展,加⼊了旋转环绕特征和对⾓线特征:如下图⾓的矩形特征。扩展后的特征⼤致分为4种类型:边缘特征、线特征环、中⼼特征模板的特征值定义为:模板内⽩⾊矩形像素和减去⿊⾊矩形像素和接下来就需要求解特征个数和特征值。2.1 矩形特征个数如图所⽰的⼀个m*m⼤⼩的⼦窗⼝,可以计算在这么⼤的⼦窗⼝内存在多少个矩形特征。特征模板可以在⼦窗⼝内以“任意”尺⼨“任意”放置,每⼀种形态称为⼀个特征。找出⼦窗⼝所有特征,是进⾏弱分类训练的基础。对于 mm×mm ⼦窗⼝,我们只需要确定了矩形左上顶点

矩形还必须满⾜下⾯两个条件(称为条件,满⾜矩形模板的在不同的尺⼨,都可以将图⽚完整划分成多个矩形。如下图特征模板和对应的(s,t)条件: 和右下顶点,即可以确定⼀个矩形。如果这个条件的矩形称为条件矩形,即在x⽅向和y⽅向可以被s和t整除。这样就可以模板1对应的是(1,2)条件,所以,x⽅向可以被1整除,y⽅向可以被2整除就可以,这样就把(50x100)图⽚划分成多个50*50个⼩格;再将模板按照倍数放⼤(横纵倍数可以不同)=====》(1,4),这样⼜可以把这个(50x100)的图⽚划分成50*25个⼩格,以此类推,直到不能再放⼤模板位置。这样得到的每个矩形⼩格都代表每种特征,此时所有⼩格的个数就是矩形特征的个数。下⾯以24×24⼦窗⼝和⼀下五种模板为例,具体计算其特征总数量:下⾯列出了,在不同⼦窗⼝⼤⼩内,特征的总数量:2.2 积分图在获取了矩形特征后,要计算矩形特征的特征值。Viola等⼈提出了利⽤积分图求特征值的⽅法。积分图的概念可⽤下图表⽰:在上图中,表⽰点A(x,y)的积分图,指的是从(1,1)到A(x,y)的图像像素之和。如上图,SAT(1)表⽰A区域的像素之和,SAT(2)表⽰A+B区域的像素之和,SAT(3)表⽰A+C区域的像素之和,SAT(4)表⽰A+B+C+D区域的像素之和。所以D区域的像素之和 。所以,⼀个区域的像素值,可以由区域的积分图计算。使⽤模板将图像划分⽹格后,就可以利⽤积分图计算每个区域的像素值,这中⽅法⽐计算像素值要快很多。如下图,使⽤模板中的2号模板(s,t)为(2,1)将图像划分⽹格:A和B区域代表着举⾏模板,所以A的像素值使⽤积分图计算:;B区域的像素值为:。。那么AB区域的特征模板的特征值为A区域像素值减去B区域像素值:所以,矩形特征的特征值,⾄于矩形端点的积分图有关,与坐标⽆关。计算端点的积分图,再加减运算,就可以得到特征值,运算速度⼤⼤提⾼,检测速增加。

3. Adaboost算法流程如上述,adaboost采⽤迭代的⽅法,⽤不同训练集训练同⼀个弱分类器,然后再把不同训练集得到的弱分类器集合在⼀起,构成⼀个强分类器,组后再把⼏组强分类器联在⼀起构成⼀个分类器。3.1 弱分类器训练弱分类器数学结构如下:其中f为特征,θ为阈值,p指⽰不等号的⽅向,x该表⼀个检测⼦窗⼝。对每个特征f,训练⼀个弱分类器h(x,f,p,θ),就是确定f的最优阈值,使得这个弱分类器 h(x,f,p,θ)对所有训练样本的分类误差最⼩。弱分类器训练的过程⼤致分为如下⼏步:  1)对每个特征f,计算所有训练样本的特征值;  2)将特征值排序;  3)对排好序的每个元素计算:    3.1)全部正例的权重和T+;    3.2)全部负例的权重和T−;    3.3)该元素前正例的权重和S+;    3.4)该元素前负例的权重和S−. 4)选取当前元素的特征值脸(或⼈脸)。该阈值的分类误差为:和它前⾯的⼀个特征值之间的数作为阈值,所得到的弱分类器就在当前元素处把样本分开 —— 也就是说这个阈值对应的弱分类器将当前元素前的所有元素分为⼈脸(或⾮⼈脸),⽽把当前元素后(含)的所有元素分为⾮⼈于是,通过把这个排序表从头到尾扫描⼀遍就可以为弱分类器选择使分类误差最⼩的阈值(最优阈值),也就是选取了⼀个最佳弱分类器。3.2. 强分类器训练在训练强分类器中,个强分类器。AdaBoost算法流程如下:,其中实例空间,⽽实例空间,。AdaBoost算法的⽬的就是从训练数据中学习⼀系列弱分类器,然后将这些弱分类器组合成⼀

简单来说,AdaBoost有很多优点:  ● AdaBoost是⼀种有很⾼精度的分类器;  ● 可以使⽤各种⽅法构建⼦分类器,AdaBoost算法提供的是框架;  ● 当使⽤简单分类器时,计算出的结果是可以理解的。⽽且弱分类器构造极其简单;  ● 简单,不⽤做特征筛选;  ● 不⽤担⼼过拟合。

4. 使⽤Opencv实现⼈脸检测OpenCV⾃带的AdaBoost程序能够根据⽤户输⼊的正样本集与负样本集训练分类器,常⽤于⼈脸检测,⾏⼈检测等。它的默认特征采⽤了Haar,不⽀持其它特征。这次实现的是⼈脸检测,⾸先是需要安装opencv库,可以从此下载,安装。找到opencvsourcesdatahaarcascades中的haarcascade_frontalface_⽂件,此⽂件是opencv中已经训练好的⼈脸adaboost联级分类器,只需要解析此⽂件即可对图像进⾏检测是否存在⼈脸,以及检测框的位置。可以将此⽂件复制到项⽬路径下。导⼊分类器的⽅法是使⽤CascaClassifter函数,即:eClassifier('./haarcascade_frontalface_')使⽤face_MultiScale(image,scaleFactor,minNeighbors,flags,minSize,maxSize)进⾏识别,例:faceRects = face_MultiScale(image, 1.05, 2, E_SCALE_IMAGE, minSize_1)image:是待检测图像scaleFactor:前后两次相继的扫描中,搜索窗⼝的⽐例系数minNeighbors:构成检测⽬标的相邻矩形的最⼩个数。minSize:⽬标的最⼩尺⼨maxSize:⽬标的最⼤尺⼨下⾯是使⽤haar+adaboost实现的⼈脸识别案例:先上效果:再上代码部分:829303132# coding:utf-8import cv2import numpy as np

[x, y, w, h] = [0, 0, 0, 0]

path = './face_images/2008_'

face_Cascade = eClassifier("./haarcascades/haarcascade_frontalface_")

frame = (path)

size = [:2]image = (size, dtype=32)image = or(frame, _BGR2GRAY)

# 直⽅图均衡image = zeHist(image)im_h, im_w = sizeminSize_1 = (im_w // 10, im_h // 10)faceRects = face_MultiScale(image, 1.05, 2, E_SCALE_IMAGE, minSize_1)if len(faceRects) > 0: for faceRect in faceRects: x, y, w, h = faceRect gle(frame, (x, y), (x + w, y + h), [255, 255, 0], 2)

("detection", frame)y(0)print('okay')

同时还可以改造成视频内的⼈脸检测,如下:829363738394041424344# coding:utf-8import cv2import numpy as np

[x, y, w, h] = [0, 0, 0, 0]

video_capture = apture("./video/hamilton_4")# video_capture = apture(0)

face_Cascade = eClassifier("./haarcascades/haarcascade_frontalface_")

indow("Face Detection System")

while video_ed(): ret, frame = video_()

if not ret: break

size = [:2] image = (size, dtype=32) image = or(frame, _BGR2GRAY)

# 直⽅图均衡 image = zeHist(image) im_h, im_w = size minSize_1 = (im_w // 8, im_h // 8) faceRects = face_MultiScale(image, 1.05, 2, E_SCALE_IMAGE, minSize_1) if len(faceRects) > 0: for faceRect in faceRects: x, y, w, h = faceRect gle(frame, (x, y), (x + w, y + h), [0, 255, 0], 2)

("Face Detection System", frame) key = y(5) if key == int(30): break

video_e()yWindow("Face Detection System")

发布者:admin,转转请注明出处:http://www.yc00.com/xiaochengxu/1690905831a460035.html

相关推荐

发表回复

评论列表(0条)

  • 暂无评论

联系我们

400-800-8888

在线咨询: QQ交谈

邮件:admin@example.com

工作时间:周一至周五,9:30-18:30,节假日休息

关注微信