从佳佳到表情识别

从佳佳到表情识别

佳佳机器人是中科大陈小平老师团队的作品,号称 “中国第一美女机器人”。今天我们以佳佳为基础,来谈一谈表情的识别。

首先有请“佳佳”自我介绍:
“大家好,我是佳佳,身高1.6米,体重90多斤,是个可爱的萌妹子。我可以进行人机对话,进行握手等行为,说话的时候口型也会匹配,还可以根据与用户的交互来表现我的高兴或者沮丧等情感。我曾担任过2016“首届全球华人机器人春晚”和“谁是棋王”半决赛的主持人呢。”

表情反馈

目前的“佳佳”已经具备了一些简单的微表情,我们先来看整个表情反馈系统的流程图,如下图所示:

这里写图片描述

在这个系统流程中,首先要获取用户的行为信息。用户的行为包括哪些呢?换言之,“佳佳”可以感受到的信息是什么?用户的语音,肢体动作,面部表情,甚至是触感都可以作为输入的信息。可以看出,输入的信息类型是多元化的。对于每一种类型的信息称之为一种模态,于是就有了多模态的信息输入;对于中间算法的处理过程我们先抛开不看;最后“佳佳”做出表情的反馈。

这里我们只考虑其中一个模态–表情相关的部分,于是整个过程可以简化为三个步骤:

(1)进行用户相关数据的采集,这里是用户的面部图像;

(2)利用设计好的算法对采集到的面部图像进行识别判断,确认用户的情感;

(3)“佳佳”做出相应的反馈,即佳佳展现出的相应的表情。

我们主要来探索表情本身,佳佳的表情系统也是整个863计划中的一个子课题。实际上,人类的情感可不是单纯的凭借六种基本表情(快乐、伤心、恐惧、愤怒、惊讶和厌恶)就可以完全衡量的。

想想我们经常用到的带有“笑”字的词语:微微一笑、眉开眼笑、开怀大笑、捧腹大笑,同样都是“笑”,但“笑”的程度是截然不同的。于是,对于表情就有了强度这一属性,用以衡量不同的程度。还有一个词语,叫做“哭笑不得”,这说明人类的表情在某一时刻并不是单一的,而是多种基本表情的组合。嫣然一笑是女子脉脉含情,笑里藏刀是小人口蜜腹剑,相视而笑是友谊地久天长,同样是笑背后的语义却又是如此的多样。综上,我们需要考虑三个问题:

  1. 表情的强度问题;
  2. 某一表情是多种基本表情的组合;
  3. 同一表情表示的语义是多样化的。

上述提到的三个问题,无论是在第(2)步中,还是在第(3)步中都是要考虑的,要准确判断用户的情感及其表达的情感的程度。相应的,“佳佳”要准确地表达出情感及其程度。

对于前两个问题,我们做出这样地定义:可以使用一个六维的向量表示某种表情是否存在,比如,使用[1,0,0,0,0,0]表示快乐。如果考虑强度的话,可以变成这样,[2.5,0,0,0,0,0],值越大表示越强。同时可以设置一个范围[0,5],进一步的,也可以将连续的强度值变为离散的:0(代表小于0.5),1(代表大于0.5,小于1.5),2(代表大于1.5,小于2.5),3(代表大于2.5,小于3.5),4(代表大于3.5,小于4.5),5(代表大于4.5,小于5)。同样的可以表示多种强度的情况:[2.5,1.1,0,0,0]。

对于最后一点我们可以尝试使用其它模态的信息来辅助进行判断,比如结合用户的语音,肢体动作和面部的图像,综合判断用户的情感。

面部动作单元

前面我们讨论的方式是直接对面部表情进行衡量,实际上还有着间接的方式。和喜欢的她走在街头,突然看到她嘴角上扬,你意识到她在对你笑。于是你开始思考,嘴角上扬和微笑是不是有什么关系呢?进一步的,面部表情是不是可以用面部肌肉的变化来衡量呢?研究人员发现,面部肌肉的动作是和表情有很大关系的。经过研究,面部由一些面部动作单元(action unit,简称AU)组成,如图3:

这里写图片描述

图3给出了一些常用的AU,实际上的AU数量是远多于这些的。AU的出现与表情有着直接的关系。比如,当一个人快乐的时候,AU12就会出现;当一个人惊讶的时候,AU1、AU2、AU5和AU26就常常会出现。因此我们也可以利用识别这些AU的存在与否来确定用户的表情。同样的,对于AU也可以定义强度这个属性,用于表示AU出现的程度,直观上就是面部动作单元的肌肉的动作程度。由此也可以利用识别AU的强度来判断表情的强度。

表情识别demo

“纸上得来终觉浅,绝知此事要躬行”。现在让我们一起来利用卷积神经网络来实现一个表情识别的demo吧。

(1)数据集。首先我们需要先下载一个数据集,这个数据集是GENKI-4K数据库,包含4000张面部图片,由不同的人,光照,位置,拍摄条件组成。所有的图片都被标记为1(微笑)或者0(没有微笑)。所以实际上这是一个二分类的问题。但是为了程序的可扩展性,我们在实现时按照多分类的方式进行处理。

(2)预处理。利用Opencv 将数据集中的面部截取出来,然后将RGB图转化为灰度图(并不是必须的步骤,只是为了加快训练。原因在于RGB图有三个通道,灰度图只有一个通道,由此降低了计算的复杂性,当然也会丢失少量的信息)。

(3)训练集和测试集。将GENKI-4K数据库划分为训练集和测试集(简单起见,我们没有用验证集),随机选择GENKI-4K数据库其中的800张图片作为测试集,其余的作为训练集。使用tensorflow的tfrecord格式来存储这些图片,可以大大减少存储的体积,加快IO速度。

(4)卷积神经网络。现在来设计我们所需要的卷积神经网络,如图4:

这里写图片描述

损失函数使用交叉熵:

def  create_loss(source_labels,pred_labels):
    ####################
    # Create loss #
    ####################
    cost= tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(
        labels=source_labels,  logits=pred_labels))
    return cost

博主特地实现了demo所有的代码,想要一起学习的朋友们可以在我的公众号中输入“FER”获取。

猜你喜欢

转载自blog.csdn.net/cassiePython/article/details/81705846