实战教程
编辑整理:萝卜兔
本文将介绍如何用神经网络将真人大头照生成卡通表情包。具体来说,我测试了VGG16 Face,这是一个用来进行人脸识别的网络,主要是为了看看真人大头照和Memoji进行比较时的效果如何。然后用它来选择新的特征和创建新的Memoji。
前言
上面的图片显示了几个结果。虽然结果没有那么完美,但是还是抓住了一些有趣的细节,说明这个简单的方法其实是有用的。我不是很确信,网络有没有把这些表情包看作是人脸。这里还有几点因素对我们的工作有影响:
漫画
首先是卡通人物看起来像真人的问题。漫画往往会夸大人物最鲜明的特征。而一些特征又往往不是人们固有的,比如说发型,并且照片上和日常中的同一个人也可能出现很大的变化。出于这个原因,神经网络很有可能会用比较抽象的方式来捕捉关于发型的特征,从而适应这种变化。而这也许就意味着它可能不适合从随意生成发型。
肤色和头发
让神经网络从随机照明条件下拍摄的照片中推断肤色是很难得的,我做了一个简单的测试工作来就可以了解这一点。在我的测试中,网络总是选择肤色较浅的选项,并不能总是很好的区别现实与不现实的选项。虽然测试网络在区分深色和浅色头发方面表现还不错,但是当它呈现色彩鲜艳的头发时却不尽人意。
这篇关于使面部特征和肤色正常化的文章很不错:https://arxiv.org/pdf/1701.04851.pdf
没有API
使用表情包进行实验受到一些限制:目前没有用于在程序上创建它们的现成API。(没有直接的方法可以在IOS中自动创建)这限制了我们在生成过程中搜索可能的Memoji空间的效率。理想情况下,我们希望使用遗传算法来尽可能地完善特征组合,而不是依赖它们的可分离性,但是这在这么简单的实验中不可行。
真人照片选择
选择哪些照片作为参考资料会对结果产生很大的影响。有些照片在主观上比其他照片产生更好的结果,我甚至也想不明白这是为什么。总的来说应该找一些比较有代表性的照片,紧密剪裁的正面面部照片。对于每个选项,我基于至少四张参考照片平均得分。
网络和设置
这些测试的实际代码很小,我将完成设置并最后链接到源代码。
VGG
VGG是一种比较流行的卷积神经网络架构,应用于图像识别领域。VGG Face则是一种专门用于人脸识别的VGG架构。该网络是现成的:
http://www.robots.ox.ac.uk/~vgg/software/vgg_face/
通过上述链接可以下载。有现成的网络就能帮助实现很多实验。
Torch
完成该测试,我使用的是Torch框架,Torch提供运行VGG模型需要的环境。它提供了一个Lua脚本环境,带有在Tensors上执行数字运算的库和用于神经网络层的原始构建块。我选择Torch,只是因为我习惯用它。
Torch上加载VGG Face模型的基本代码:
加载和规范化图像涉及几个步骤,可以在源代码中找到。
Working with the Layers
如上图所示,VGG由不同类型的层组成。输入是一张RGB的图像,经过一系列卷积、池化、加权和其他类型的变换。随着每个层逐渐学习更多抽象特征,数据的“形状”和维度也会发生变化。最终,网络最后一层产生一个2622维的预测向量。这个向量表示网络训练使用的2622个人的概率分布。
在我们的实验中,我们并不关心预测的结果,而是想用神经网络来比较我们的人脸集。因此,我们可以倒数第二层,该层输出4096维的向量来表示面部特征。
虽然VGG通常是16层,但是Torch(及其神经网络库)实际上包括40个“module”,而第38个module是我们想要的。
Similarity
我们要做的主要是通过网络运行图像对,并使用简单的相似性度量比较各自的输出。比较两个非常大的向量的一种方法是使用点积:
这会产生一个标量值,可以将其视为表示向量在其高维空间中的“对齐”程度。
对于该实验,我们希望将预期的表情和多个参考图像进行比较并组合结果。为此,我只是将每对的值标准化并将它们平均以产生一个“分值”。
标准化是用图像与其自身进行比较,产生的分值为1.0。如果后面得到的分值更大,则意味着相似性更高。
我们也可以使用许多其他类型的指标,比如欧式距离或者是输出之间的均方差。我尝试使用了这两个指标,相比之下,点积的效果更好,我也不太明白这是为什么。
A First Test - The Lineup
首先要验证的事情是人脸识别网络能不能对卡通头像有作用。我从Google图像中随机收集了63个比较像人的大头像(其中大部分来源于Apple)。
然后,我选择其中一个,并让网络通过上述的相似性计算对所有Memoji进行排名,展示相似度最高的三个。
结果还是比较好的,网络不仅找到了相同的Memoji(排名第一,得分为1.0)而且,我们可以看到,第二名和第三名的选择也还算合理。
真实照片
现在我们来看真正的实验:神经网络将如何匹配真实照片和Memoji呢?我抓取了一些名人照片,结果如下:
结果非常有趣!(有点好笑)但是不要忘了,我们的网络可以选择的Memoji图集是一个很有限的数据集,并且网络在这些图像中看到的主要特征可能不是我们期望的。
来我们继续!
The “Generation”Process
接下来,我们尝试使用网络来选择特征来创建Memoji。这就是比较麻烦的地方,前面也提到过,没有方法在iOS上自动创建Memoji。
测试装备是QuickTime Player的电影录制功能将我的手机连接到我的桌面,并将其放置在可以抓去屏幕截图进行处理的地方。对于每个特征,我都会检查各种可能性,选择每个选项并获取输出,对其进行排名。
这个方法不现实,首先这简直太痛苦了。(比如说,光是发型就有93种;尝试运行了几十次)更重要的是,它只允许我们一次评估一个特征。从理论上讲,我们可以就此进行迭代,并重复运行,直到网络没有建议为止,但即使这样也不完美,因为它只是基于我们如何开始的“局部最优”。(如果特征之间会相互影响,那么评估的顺序也很重要。)
结果
开头我已经说了实验的结果,但是这里我将说更多细节。
本文中,特朗普的形象,其中关于头发的选择是我指导选择了一个排名更高的头发。这里所有的图像都是来自脚本的选择。
话虽如此,但是有些特征还是更加不稳定。比如,在某些情况下,网络做出的前三个选择很相似,但有的时候却不是。比如,下面是特朗普头发选择的前三名:
而一些特征的选择很符合我的预期。比如奥巴马有比较突出的耳朵,网络确实前三名分别由大到小:
但是眼睛的选择变化却很大:
相比之下,特朗普的眼睛更加一致:
头发颜色
我已经提及过肤色没有太多的影响。(虽然好像网络也做了一些尝试)。
头发颜色也存在问题。虽然展示的特朗普和奥巴马的发色都还OK,但是如果是一些颜色特别鲜艳的图像,网络总是优先选择灰色:
虽然,红色头发能在前三或者前十名找到,但是这并不让人满意。我做了很多尝试试图找到原因,比如改变图片预处理图片的方式,但是这并没有什么用,灰色仍然是一个很稳定的选择。
然后我选择用第32层的输出,虽然这在挑选红头发上表现更好,但是对其他特征的处理却更加糟糕得多。
我也尝试了以各种方式(通过前三种选择和备用网络层)平均发色选择,但是这比较模糊,反正最终比较鲜艳的头发颜色特征选择还是不太成功。
如果有什么很好的想法或者处理方式,请写信给我呀!
资源
VGG-Memoji:
https://github.com/patniemeyer/vgg-memoji
Visual Geometry Group VGG Face:
http://www.robots.ox.ac.uk/~vgg/software/vgg_face/
>
领取专属 10元无门槛券
私享最新 技术干货