机器学习: Viola-Jones 人脸检测算法解析(一)
在计算机视觉领域中,人脸检测或者物体检测一直是一个非常受关注的领域,而在人脸检测中,Viola-Jones人脸检测算法可以说是非常经典的一个算法,所有从事人脸检测研究的人,都会熟悉了解这个算法,Viola-Jones算法在2001年的CVPR上提出,因为其高效而快速的检测即使到现在也依然被广泛使用,OpenCV 和 Matlab中都将这个算法写进了函数库可以很方便的直接调用。虽然VJ人脸检测算法最初都是用来检测正面的人脸图像,对于侧脸图像的检测不是很稳健,不过这个算法依然有值得研究的价值。
这个算法包含以下几个重要的部分:
1 利用Haar 特征描述人脸的共有属性;
2 建立了一种称为积分图像的特征,并且基于积分图像,可以快速获取几种不同的矩形特征;
3 利用Adaboost 算法进行训练;
4 建立层级分类器。
利用Haar 特征描述人脸的共有属性
一般来说,人脸会有一些基本的共性,比如眼睛区域会比脸颊区域要暗很多,鼻子一般属于脸部的高光区域,鼻子会比周围的脸颊要亮很多,一张正脸图像,眼睛,眉毛,鼻子,嘴巴等的相对位置是有规律可循的。Haar 特征考虑的是某一特定位置相邻的矩形区域,把每个矩形区域的像素相加然后再相减,总得来说,基本对应以下几种情形:
我们以前都是针对单一像素做,现在需要针对矩形区域,相当于是把单个像素变成矩形区域,所以要对每个矩形区域先求和,然后再利用上面的算子做运算,这种特征称之为Haar-like 特征。
积分图像与矩形特征
正如上一节所说,为了计算Haar-like特征,需要对矩形区域的所有像素求和,一个图像所能形成的矩形区域有大有小,如果每个矩形区域都用遍历所有像素再求和的运算方法,无疑这个运算负担将非常巨大,所有VJ人脸检测算法用到了一种非常巧妙的数据结构,称为integral image(积分图像),积分图像的原理非常简单,总得来说,就是对于图像中的任何一点,该点的积分图像值等于位于该点左上角的所有像素之和,表达式如下:
并且积分图像满足如下关系:
其中I 表示积分图像,f 表示原来的图像,x,y,x′,y′表示像素的位置。所以一张图像的积分图像记录了这张图像上每一个像素点其左上角所有像素的和,如果把一张图像的左上角看做坐标原点,那么上面的表达式就是原点到该像素点之间的所有像素点的离散求和,这可以看成是一种积分,所以这也是积分图像名称的由来。 利用积分图像,我们可以计算一张图像上任意一个矩形区域的像素和,积分图像的计算matlab 有一个库函数integralImage 可以直接调用,
I=intergralImage(img)
如下图所示,左边的图表示人脸图像,右边的图表示归一化之后积分图像。
有了积分图像,就可以很方便的计算图像中任何一个矩形区域的像素和,如下图所示:
为了计算矩形ABCD的像素和,利用积分图像可以表示如下:
这意味着,任何一个矩形区域的像素和,都可以由积分图像 I 上面的四个点来表示。VJ人脸检测算法用到了三种不同的矩形特征,分别是二邻接,三邻接,四邻接矩形,如下图所示:
很显然一个矩形可以由四个点来表示,二邻接矩形需要六个点表示,三邻接矩形需要八个点,而四邻接矩形需要九个点。
下面我们来看看,给定一张图像,有多少个矩形特征,VJ 算法里用到的是 24×24 的图像大小,我们可以计算一个24×24 的图像可以产生多少矩形特征。考虑水平方向与垂直方向,二邻接矩形有两种情况1×2 和 2×1,三邻接矩形也有两种情况 1×3 和 3×1,而四邻接矩形只有一种情况2×2。
下面列出每种邻接矩形可能的size大小。
二邻接矩形 (1×2): 1×2, 1×4, 1×6, … 1×24 , 2×2, 2×4, 2×6, … 2×24 … 24×24 矩形的长以2的倍数增加,宽逐渐增加。
三邻接矩形 (1×3): 1×3, 1×6, 1×9, … 24×24 矩形的长是以3的倍数增加,宽逐渐增加。
四邻接矩形 (2×2): 2×2, 2×4, 2×8, 2×16, … 24×24 矩形的长宽都是以2的倍数增加。
根据卷积定理,我们知道一个W×H 的图像与 m×n 的filter 做卷积,新生成的图像大小为
(W−m+1)×(H−n+1), 新图像的每一个像素其实就是原图一个m×n 的local patch与 m×n 的filter 的乘积和。新图像有多少个像素,就对应着原图多少个m×n 的矩形。
我们用一段代码来求一个24×24 图像会产生多少个矩形特征: 因为 1×2 和 2×1 的情形是一样的,1×3 和 3×1 的情形也是一样,所以我们只要分别计算一种情况,再乘以2就行了。
import numpy as np
a = np.zeros((3, 2), dtype=int)
Count = np.zeros(3, dtype=int)
a[0, :] = [1, 2]
a[1, :] = [1, 3]
a[2, :] = [2, 2]
Img_size = 24
for ii in range(3):
rec_h = a[ii, 0]
rec_w = a[ii, 1]
for xx in range(rec_h, Img_size+1, rec_h):
for yy in range(rec_w, Img_size+1, rec_w):
Count[ii] = Count[ii]+(Img_size-xx+1)*(Img_size-yy+1)
print Count[ii]
Total = Count[0]*2+Count[1]*2+Count[2]
print ("Total: ", Total)
最后可以得到:
1×2: 43200
1×3: 27600
2×2: 20736
所以最终总的矩形特征为 43200×2+27600×2+20736=162336
可以看到,一个 24×24 的图像最终会产生162336个矩形特征,这个维度远远高于图像本身的维度。不可能将所有的矩形特征都用,所有需要做特征选择,下一篇,我们将探讨如何利用AdaBoost来做特征选择与训练。
机器学习: Viola-Jones 人脸检测算法解析(一)的更多相关文章
- 机器学习: Viola-Jones 人脸检测算法解析(二)
上一篇博客里,我们介绍了VJ人脸检测算法的特征,就是基于积分图像的矩形特征,这些矩形特征也被称为Haar like features, 通常来说,一张图像会生成一个远远高于图像维度的特征集,比如一个 ...
- 重磅!刷新两项世界纪录的腾讯优图人脸检测算法DSFD开源了!
近日,知名开源社区Github上有个名为DSFD(Dual Shot Face Detector)的算法引起了业内关注,它正是来自于腾讯优图.目前,该算法已经被计算机视觉顶级会议CVPR 2019接收 ...
- Python机器学习笔记:异常点检测算法——LOF(Local Outiler Factor)
完整代码及其数据,请移步小编的GitHub 传送门:请点击我 如果点击有误:https://github.com/LeBron-Jian/MachineLearningNote 在数据挖掘方面,经常需 ...
- 基于Adaboost的人脸检测算法
AdaBoost算法是一种自适应的Boosting算法,基本思想是选取若干弱分类器,组合成强分类器.根据人脸的灰度分布特征,AdaBoost选用了Haar特征[38].AdaBoost分类器的构造过程 ...
- 机器学习--详解人脸对齐算法SDM-LBF
引自:http://blog.csdn.net/taily_duan/article/details/54584040 人脸对齐之SDM(Supervised Descent Method) 人脸对齐 ...
- 吴恩达机器学习笔记55-异常检测算法的特征选择(Choosing What Features to Use of Anomaly Detection)
对于异常检测算法,使用特征是至关重要的,下面谈谈如何选择特征: 异常检测假设特征符合高斯分布,如果数据的分布不是高斯分布,异常检测算法也能够工作,但是最好还是将数据转换成高斯分布,例如使用对数函数:
- yolo类检测算法解析——yolo v3
每当听到有人问“如何入门计算机视觉”这个问题时,其实我内心是拒绝的,为什么呢?因为我们说的计算机视觉的发展史可谓很长了,它的分支很多,而且理论那是错综复杂交相辉映,就好像数学一样,如何学习数学?这问题 ...
- win10+anaconda+cuda配置dlib,使用GPU对dlib的深度学习算法进行加速(以人脸检测为例)
在计算机视觉和机器学习方向有一个特别好用但是比较低调的库,也就是dlib,与opencv相比其包含了很多最新的算法,尤其是深度学习方面的,因此很有必要学习一下.恰好最近换了一台笔记本,内含一块GTX1 ...
- 基于AdaBoost算法——世纪晟结合Haar-like特征训练人脸检测识别
AdaBoost 算法是一种快速人脸检测算法,它将根据弱学习的反馈,适应性地调整假设的错误率,使在效率不降低的情况下,检测正确率得到了很大的提高. 系统在技术上的三个贡献: 1.用简单的Haa ...
随机推荐
- 利用VS安装项目打包软件的做法
作者:朱金灿 来源:http://blog.csdn.net/clever101 昨天摸索了一下,发现使用VS安装项目来打包软件还是挺方便的. 1. 创建一个安装项目工程,如下图: 2. 设置工程属性 ...
- eclipse调试鼠标放上去显示变量值
在eclipse中调试时,鼠标移动到变量上不显示值,这个原来自己也遇到过,没注意,反正就使用ctrl+shift+i嘛,也可以的,刚查了一下,解决方法如下: Window->Preference ...
- Pandoc —— 标记语言转换工具(中文乱码问题)
今次毕业设计,来个逼格高的,用 latex 编写.谁曾想,学院首先要收一份 word 版的.辣么多的 latex 公式如何转呀. Pandoc 是由 John MacFarlane 开发的标记语言转换 ...
- JDK8 JVM性能优化-1
原文地址:https://blog.csdn.net/xingkongtianma01/article/details/80689928 大 多数情况下,我们并不需要关心JVM的底层,但是如果了解它的 ...
- openstack中虚拟机怎么与物理机通信
How-to-connection-ns-outside 环境配置 网络接口 vi /etc/sysconfig/network-scripts/ifcfg-eth0 DEVICE=eth0 TYPE ...
- 8大排序算法图文讲解 分类: B10_计算机基础 2014-08-18 15:36 243人阅读 评论(0) 收藏
排序算法可以分为内部排序和外部排序,内部排序是数据记录在内存中进行排序,而外部排序是因排序的数据很大,一次不能容纳全部的排序记录,在排序过程中需要访问外存. 常见的内部排序算法有:插入排序.希尔排序. ...
- Tricks(四十九)—— 按 batch 访问越界的解决办法
使用 min 函数指定访问的最终位置,本质上是增加一个条件判断: done = false; batch_size = 10000; idx = 1; while ~done idx_end = mi ...
- php汉字字符串长度和截取
mb_strlen("你好123",'utf-8');//返回5 strlen("你好");//返回几我也不知道,肯定不是2,但你想要2就用上面的 substr ...
- 【前端统计图】hcharts实现堆叠柱形图(与后台数据交互)
原型图类似如下: 图片.png <!DOCTYPE > <html> <head> <meta charset="utf-8">&l ...
- PHP移动互联网开发笔记(8)——MySQL数据库基础回顾[2]
一.数据表 为了确保数据的完整性和一致性,在创建表时指定字段名称,字段类型和字段属性外,还需要使用约束(constraint),索引(index),主键(primary key)和外键(foregin ...