参考网址:https://sefiks.com/2018/01/01/facial-expression-recognition-with-keras/
1.数据集介绍及处理:
(1) 数据集Fer2013下载地址为:https://www.kaggle.com/c/challenges-in-representation-learning-facial-expression-recognition-challenge/data
该数据集中每张图片的像素为48*48,该数据集用excel读取后显示的格式如下图所示:
第一列为标签(也即为什么表情),第二列为像素值,第三列是代表该图片是训练集还是测试集,已经给你打乱了。只需要用即可
(2)pandas读取数据集
import numpy as np import pandas as pd data = pd.read_csv('data/fer2013/fer2013.csv') num_of_instances = len(data) #获取数据集的数量 print("数据集的数量为:",num_of_instances) pixels = data['pixels'] emotions = data['emotion'] usages = data['Usage']
(3)分离训练集和测试集
num_classes = 7 #表情的类别数目 x_train,y_train,x_test,y_test = [],[],[],[] for emotion,img,usage in zip(emotions,pixels,usages): try: emotion = keras.utils.to_categorical(emotion,num_classes) # 独热向量编码 val = img.split(" ") pixels = np.array(val,'float32') if(usage == 'Training'): x_train.append(pixels) y_train.append(emotion) elif(usage == 'PublicTest'): x_test.append(pixels) y_test.append(emotion) except: print("",end="")
(4)把数据集转换为numpy数组格式,方便后续处理
x_train = np.array(x_train) y_train = np.array(y_train) x_train = x_train.reshape(-1,48,48,1) x_test = np.array(x_test) y_test = np.array(y_test) x_test = x_test.reshape(-1,48,48,1)
(5)显示其中的前4张图片
import matplotlib.pyplot as plt %matplotlib inline for i in range(4): plt.subplot(221+i) plt.gray() plt.imshow(x_train[i].reshape([48,48]))
2. 创建网络 进行训练和测试
from keras.models import Sequential from keras.layers import Conv2D,MaxPool2D,Activation,Dropout,Flatten,Dense from keras.optimizers import Adam from keras.preprocessing.image import ImageDataGenerator batch_size = 8 epochs = 20 model = Sequential() #第一层卷积层 model.add(Conv2D(input_shape=(48,48,1),filters=32,kernel_size=3,padding='same',activation='relu')) model.add(Conv2D(filters=32,kernel_size=3,padding='same',activation='relu')) model.add(MaxPool2D(pool_size=2, strides=2)) #第二层卷积层 model.add(Conv2D(filters=64,kernel_size=3,padding='same',activation='relu')) model.add(Conv2D(filters=64,kernel_size=3,padding='same',activation='relu')) model.add(MaxPool2D(pool_size=2, strides=2)) #第三层卷积层 model.add(Conv2D(filters=128,kernel_size=3,padding='same',activation='relu')) model.add(Conv2D(filters=128,kernel_size=3,padding='same',activation='relu')) model.add(MaxPool2D(pool_size=2, strides=2)) model.add(Flatten()) #全连接层 model.add(Dense(64,activation = 'relu')) model.add(Dropout(0.5)) model.add(Dense(7,activation = 'softmax')) #进行训练 model.compile(loss = 'categorical_crossentropy',optimizer = Adam(),metrics=['accuracy']) model.fit(x_train,y_train,batch_size=batch_size,epochs=epochs) train_score = model.evaluate(x_train, y_train, verbose=0) print('Train loss:', train_score[0]) print('Train accuracy:', 100*train_score[1]) test_score = model.evaluate(x_test, y_test, verbose=0) print('Test loss:', test_score[0]) print('Test accuracy:', 100*test_score[1])
这是一种通用识别架构,由于我的电脑配置不行,程序正在训练,不再贴运行结果。可自行修改网络架构。
程序中需要注意的地方:同时遍历多个数组或列表时,可用zip()函数进行遍历。