本身动手制做“平均脸”【1】


有趣的“平均脸”


你们想必看到过不少合成的“平均脸”图片吧。


有按国家、民族合成的:



也有针对政要明星合成的,例如这张,韩中日三国明星平均脸:html



“平均脸”的历史python


虽然如今很流行,可是,其实平均脸的历史至关悠久。git


1878年,英国的弗朗西斯·高尔顿爵士(Sir Francis Galton)发明了一种创造出“平均”面容的技术。github


弗朗西斯·高尔顿爵士,英国维多利亚时代的博学家、人类学家、优生学家、热带探险家、地理学家、发明家、气象学家、统计学家、心理学家和遗传学家;也是《物种起源》做者查尔斯·达尔文的表弟。*web

这一方法是经过将许多人的照片合成为一张照片完成的。微信

当时具体的作法是:照片叠加——给多我的,好比20我的,照相,将每一个人照片所需的曝光时间缩短为1/20,经过20次曝光获得一张“平均”照片。spa

弗朗西斯·高尔顿最初合成平均脸的目的是将不一样“种类”的人(例如:囚犯、精神病患者等等)视觉化,以期获得这类人的“原型”(共同特征)。.net

但结果却意外的发现,这样合成的人脸却比用于合成大部分(甚至是所有)都要好看!orm

虽然高尔顿爵士的初衷没有达到,合成平均脸的方法却保留了下来。htm

新技术让人人可制做“平均脸”

随着技术的发展,照片再也不须要物理底片,合成也再也不须要复杂的曝光冲印技术,经过一些简单的操做就能作到,人人均可以上手。

想不想本身动手制做一张周围人的平均脸?

一点都不复杂,只要知道了用Image Morphing技术叠加照片原理,再会写几行简单的代码,就能顺利完成。

Image Morphing技术的原理至关简单:给定两张图片I和J,咱们经过叠加(或者叫作混合)I和J来得到一张中间状态的图片M。

I和J的叠加由一个参数[0,1]区间内的参数alpha来控制。当alpha=0时,M就等同于I,而aphla=1时,M就为J。

换言之, M中的每个像素M(x,y),均可以经过这样一个公式来获得它的值:

M(x,y) = (1 – alpha)·I(x,y) + alpha·J(x,y)

当alpha=0.5的时候,I和J就五五开,平均贡献了M。若是I和J是两张人脸照片的话,M天然也就成了它们的“平均脸”。

看起来好容易哦,那咱们赶忙找两张照片来试试吧!就用这两张:

这两张照片alpha=0.5后直接叠加的结果是这样的:

这也不是人脸呀!先别急,看看为何会这样?

从这张“重影图”上不难看出来,之因此这样,是由于最基本的五官都没有对齐。

若是咱们事先把两我的的眼睛和嘴对齐,效果就不会是这样的了。

叠加两张*对齐的*人脸

叠加图片I和图片J的时候,首先应该创建两张照片中像素的对应关系


对I中的某一个像素点(xi,yi),咱们不是直接在J中取一样位置的点就能够了,而是要找到它在J中内容上的对应点 (xj,yj)。


而后再进一步找到M中这两个点叠加以后应当处在的位置(xm,ym),最后再用下列式子得出M中对应点的像素值:


xm = (1-alpha) · xi + alpha · xj

ym = (1-alpha) · yi + alpha · yj

算式-1

对一个像素点咱们这样作,对整幅图片,则是将上面的过程运用到它的每个像素点上:

M(xm,ym) = (1 – alpha)·I(xi,yi) + alpha·J(xj,yj)

算式-2

很好,咱们已经知道从原理上该怎么叠加两张图了。

其中关键的一步就是:找到对应点

其实对应点叠加的方法能够用来叠加任何图片,不只限于人脸。

不一样物体的叠加,真正的区别就在于找到像素点之间的对应关系!一旦对应关系找到,直接运用算式-2就行了。

划分区域对应人脸

既然咱们如今要作的是叠加人脸,那么首先固然要找到人脸上的对应点。

人脸是生活中最多见的事物,咱们每个人都很是熟悉。

一我的的脸若是用简笔画画出来,能够简化为:脸型+五官(眉毛、眼睛、鼻子、嘴)。

那么若是咱们要叠加两我的的脸的话,天然就是要针对他们的脸型和五官形制求平均。

人的五官若是用图形来描绘,都是不规则图形。若是要彻底不走样的获取一我的的眼睛、眉毛、鼻子或者嘴,须要绘制很是复杂的形状。

实际上,咱们没有必要这样作,而是能够经过一种很是简单的近似方法,把一张人脸分割成若干三角形的区域,而后再来叠加两张脸上对应的三角区域。

分割方法以下:

1. 获取人脸特征


在图片中获取人脸和人脸特征(脸型+五官)。

咱们先在每张面孔上获取68个面部基准点(以下图)。


2. Delaunay 三角剖分


在得到了68个面部基准点以后,咱们结合人脸所在的矩形的四个顶点和每条边的中心点,将人脸所在的矩形分割成以下图所示的三角形的组合。


这一方法又称为Delaunay三角剖分。更多细节请看:https://www.learnopencv.com/delaunay-triangulation-and-voronoi-diagram-using-opencv-c-python/

叠加通过仿射变换的Delaunay剖分三角形


Delaunay三角剖分将图像分解成若干三角形后,再分别对齐各个三角形区域,对其中像素值进行平均。


Step-1:找到合成图片中的面部特征点

使用前述的算式-1,根据图像I和图像J中已经得到的76个点,在叠加的结果图像M中找到76个点(xm, ym)

Step-2: 计算原图到目标图像的仿射变换

如今咱们在图像I,J和M中分别获得了76个点,以及由这76个点剖分而成的三组三角形。

从图像I中选取一个三角形ti,在M中找到对应区域tm,经过ti三个顶点到tm三个顶点的映射关系来计算ti到tm的仿射变换。

同理计算出tj到tm的仿射变换。

Step-3:扭曲Delaunay剖分三角形

对于图像I中的一个三角形,使用step-2中计算出的放射变换,将其中每个像素经过仿射变换对应到M中对应的位置去。

重复这个过程,处理图像I中的每个三角形,获得一个扭曲的(warped)图像I'。用一样的方法处理图像J,得到扭曲的图像J'。

Step-4:叠加两张脸

在step-3中咱们已经获得了扭曲的图像I'和图像J'。这两个图像就能够直接使用算式-2进行叠加了。最后获得叠加结果。

叠加多张人脸


算式-2用于叠加2张人脸,在alpha=0.5时求取的是两张脸的平均。

那么咱们把算式推广一下,从图像I和图像J推广为图像I1, I2, I3, ..., In;令alpha=1/n;则算式-2变形为以下:

M(xm,ym) = 1/n · [I1(xi1, yi1) + I2(xi2, yi2) + ... ... + In(xin, yi_n)]

由此,咱们也就获得了n张脸的平均。

用这个方法,咱们能够获得6位美国总统的平均脸:

他们平均以后的样子是这样的:

上面的过程看着还挺复杂是否是?其实,若是使用opencv + dlib,只要几十行代码就能搞定!

今天先讲原理,下次咱们再来分析具体技术和代码 

代码在此:https://github.com/juliali/AverageFace

欢迎扫面下列二维码关注“悦思悦读”公众微信号

本文分享自微信公众号 - 悦思悦读(yuesiyuedu)。
若有侵权,请联系 support@oschina.cn 删除。
本文参与“OSC源创计划”,欢迎正在阅读的你也加入,一块儿分享。

相关文章
相关标签/搜索