机器学习(二)深度学习实战-使用Kera预测人物年龄

本文涉及的产品
传统型负载均衡 CLB,每月750个小时 15LCU
应用型负载均衡 ALB,每月750个小时 15LCU
网络型负载均衡 NLB,每月750个小时 15LCU
简介: 我们的任务是从一个人的面部特征来预测他的年龄(用“Young”“Middle ”“Old”表示),我们训练的数据集大约有19906多张照片及其每张图片对应的年龄(全是阿三的头像。。。),测试集有6636张图片,首先我们加载数据集,然后我们通过深度学习框架Keras建立、编译、训练模型,预测出6636张人物头像对应的年龄

问题描述


我们的任务是从一个人的面部特征来预测他的年龄(用“Young”“Middle ”“Old”表示),我们训练的数据集大约有19906多张照片及其每张图片对应的年龄(全是阿三的头像。。。),测试集有6636张图片,首先我们加载数据集,然后我们通过深度学习框架Keras建立、编译、训练模型,预测出6636张人物头像对应的年龄


引入所需要模块


import os
import random
import pandas as pd
import numpy as np
from PIL import Image


加载数据集


root_dir=os.path.abspath('E:/data/age')
train=pd.read_csv(os.path.join(root_dir,'train.csv'))
test=pd.read_csv(os.path.join(root_dir,'test.csv'))
print(train.head())
print(test.head())


ID   Class
0    377.jpg  MIDDLE
1  17814.jpg   YOUNG
2  21283.jpg  MIDDLE
3  16496.jpg   YOUNG
4   4487.jpg  MIDDLE
          ID
0  25321.jpg
1    989.jpg
2  19277.jpg
3  13093.jpg
4   5367.jpg


随机读取一张图片试下(☺)


i=random.choice(train.index)
img_name=train.ID[i]
print(img_name)
img=Image.open(os.path.join(root_dir,'Train',img_name))
img.show()
print(train.Class[i])


20188.jpg
MIDDLE


难点


我们随机打开几张图片之后,可以发现图片之间的差别比较大。大家感受下:

  1. 质量好的图片:
  • Middle:
    **Middle**


  • Young:


31.png
**Young**

  • Old:
    **Old**
  1. 质量差的:
  • Middle:33.png
    **Middle**


下面是我们需要面临的问题:

  1. 图片的尺寸差别:有的图片的尺寸是66x46,而另一张图片尺寸为102x87
  2. 人物面貌角度不同:
  • 侧脸:34.png
  • 正脸:35.png
  1. 图片质量不一(直接上图):

    36.png
    插图
  2. 亮度和对比度的差异

    37.png
    亮度

    38.png
    对比度

    现在,我们只专注下图片尺寸处理,将每一张图片尺寸重置为32x32


格式化图片尺寸和将图片转换成numpy数组


temp=[]
for img_name in train.ID:
    img_path=os.path.join(root_dir,'Train',img_name)
    img=Image.open(img_path)
    img=img.resize((32,32))
    array=np.array(img)
    temp.append(array.astype('float32'))
train_x=np.stack(temp)
print(train_x.shape)
print(train_x.ndim)


(19906, 32, 32, 3)
4


temp=[]
for img_name in test.ID:
    img_path=os.path.join(root_dir,'Test',img_name)
    img=Image.open(img_path)
    img=img.resize((32,32))
    array=np.array(img)
    temp.append(array.astype('float32'))
test_x=np.stack(temp)
print(test_x.shape)


(6636, 32, 32, 3)


另外我们再归一化图像,这样会使模型训练的更快


train_x = train_x / 255.
test_x = test_x / 255.


我们看下图片年龄大致分布


train.Class.value_counts(normalize=True)


MIDDLE    0.542751
YOUNG     0.336883
OLD       0.120366
Name: Class, dtype: float64


test['Class'] = 'MIDDLE'
test.to_csv('sub01.csv', index=False)


将目标变量处理虚拟列,能够使模型更容易接受识别它


import keras
from sklearn.preprocessing import LabelEncoder
lb=LabelEncoder()
train_y=lb.fit_transform(train.Class)
print(train_y)
train_y=keras.utils.np_utils.to_categorical(train_y)
print(train_y)
print(train_y.shape)


[0 2 0 ..., 0 0 0]
[[ 1.  0.  0.]
 [ 0.  0.  1.]
 [ 1.  0.  0.]
 ..., 
 [ 1.  0.  0.]
 [ 1.  0.  0.]
 [ 1.  0.  0.]]
(19906, 3)


创建模型


#构建神经网络
input_num_units=(32,32,3)
hidden_num_units=500
output_num_units=3
epochs=5
batch_size=128


from keras.models import Sequential
from keras.layers import Dense,Flatten,InputLayer
model=Sequential({
    InputLayer(input_shape=input_num_units),
    Flatten(),
    Dense(units=hidden_num_units,activation='relu'),
    Dense(input_shape=(32,32,3),units=output_num_units,activation='softmax')
})
model.summary()


_________________________________________________________________
Layer (type)                 Output Shape              Param #   
=================================================================
input_23 (InputLayer)        (None, 32, 32, 3)         0         
_________________________________________________________________
flatten_23 (Flatten)         (None, 3072)              0         
_________________________________________________________________
dense_45 (Dense)             (None, 500)               1536500   
_________________________________________________________________
dense_46 (Dense)             (None, 3)                 1503      
=================================================================
Total params: 1,538,003
Trainable params: 1,538,003
Non-trainable params: 0
_________________________________________________________________


编译模型


# model.compile(optimizer='sgd',loss='categorical_crossentropy',metrics=['accuracy'])
model.compile(optimizer='sgd',loss='categorical_crossentropy', metrics=['accuracy'])
model.fit(train_x,train_y,batch_size=batch_size,epochs=epochs,verbose=1)


Epoch 1/5
19906/19906 [==============================] - 4s - loss: 0.8878 - acc: 0.5809     
Epoch 2/5
19906/19906 [==============================] - 4s - loss: 0.8420 - acc: 0.6077     
Epoch 3/5
19906/19906 [==============================] - 4s - loss: 0.8210 - acc: 0.6214     
Epoch 4/5
19906/19906 [==============================] - 4s - loss: 0.8149 - acc: 0.6194     
Epoch 5/5
19906/19906 [==============================] - 4s - loss: 0.8042 - acc: 0.6305     
<keras.callbacks.History at 0x1d3803e6278>


model.fit(train_x, train_y, batch_size=batch_size,epochs=epochs,verbose=1, validation_split=0.2)


Train on 15924 samples, validate on 3982 samples
Epoch 1/5
15924/15924 [==============================] - 3s - loss: 0.7970 - acc: 0.6375 - val_loss: 0.7854 - val_acc: 0.6396
Epoch 2/5
15924/15924 [==============================] - 3s - loss: 0.7919 - acc: 0.6378 - val_loss: 0.7767 - val_acc: 0.6519
Epoch 3/5
15924/15924 [==============================] - 3s - loss: 0.7870 - acc: 0.6404 - val_loss: 0.7754 - val_acc: 0.6534
Epoch 4/5
15924/15924 [==============================] - 3s - loss: 0.7806 - acc: 0.6439 - val_loss: 0.7715 - val_acc: 0.6524
Epoch 5/5
15924/15924 [==============================] - 3s - loss: 0.7755 - acc: 0.6519 - val_loss: 0.7970 - val_acc: 0.6346
<keras.callbacks.History at 0x1d3800a4eb8>


优化


我们使用最基本的模型来处理这个年龄预测结果,并且最终的预测结果为0.6375。接下来,从以下角度尝试优化:

  1. 使用更好的神经网络模型
  2. 增加训练次数
  3. 将图片进行灰度处理(因为对于本问题而言,图片颜色不是一个特别重要的特征。)


optimize1 使用卷积神经网络


添加卷积层之后,预测准确率有所上涨,从6.3到6.7;最开始epochs轮数是5,训练轮数增加到10,此时准确率为6.87;然后将训练轮数增加到20,结果没有发生变化。


Conv2D层


keras.layers.convolutional.Conv2D(filters, kernel_size, strides=(1, 1), padding='valid', data_format=None, dilation_rate=(1, 1), activation=None, use_bias=True, kernel_initializer='glorot_uniform', bias_initializer='zeros', kernel_regularizer=None, bias_regularizer=None, activity_regularizer=None, kernel_constraint=None, bias_constraint=None)

  • filters:输出的维度
  • strides:卷积的步长

更多关于Conv2D的介绍请看Keras文档Conv2D层


#参数初始化
filters=10
filtersize=(5,5)
epochs =10
batchsize=128
input_shape=(32,32,3)


from keras.models import Sequential
model = Sequential()
model.add(keras.layers.InputLayer(input_shape=input_shape))
model.add(keras.layers.convolutional.Conv2D(filters, filtersize, strides=(1, 1), padding='valid', data_format="channels_last", activation='relu'))
model.add(keras.layers.MaxPooling2D(pool_size=(2, 2)))
model.add(keras.layers.Flatten())
model.add(keras.layers.Dense(units=3, input_dim=50,activation='softmax'))
model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])
model.fit(train_x, train_y, epochs=epochs, batch_size=batchsize,validation_split=0.3)
model.summary()


Train on 13934 samples, validate on 5972 samples
Epoch 1/10
13934/13934 [==============================] - 9s - loss: 0.8986 - acc: 0.5884 - val_loss: 0.8352 - val_acc: 0.6271
Epoch 2/10
13934/13934 [==============================] - 9s - loss: 0.8141 - acc: 0.6281 - val_loss: 0.7886 - val_acc: 0.6474
Epoch 3/10
13934/13934 [==============================] - 9s - loss: 0.7788 - acc: 0.6504 - val_loss: 0.7706 - val_acc: 0.6551
Epoch 4/10
13934/13934 [==============================] - 9s - loss: 0.7638 - acc: 0.6577 - val_loss: 0.7559 - val_acc: 0.6626
Epoch 5/10
13934/13934 [==============================] - 9s - loss: 0.7484 - acc: 0.6679 - val_loss: 0.7457 - val_acc: 0.6710
Epoch 6/10
13934/13934 [==============================] - 9s - loss: 0.7346 - acc: 0.6723 - val_loss: 0.7490 - val_acc: 0.6780
Epoch 7/10
13934/13934 [==============================] - 9s - loss: 0.7217 - acc: 0.6804 - val_loss: 0.7298 - val_acc: 0.6795
Epoch 8/10
13934/13934 [==============================] - 9s - loss: 0.7162 - acc: 0.6826 - val_loss: 0.7248 - val_acc: 0.6792
Epoch 9/10
13934/13934 [==============================] - 9s - loss: 0.7082 - acc: 0.6892 - val_loss: 0.7202 - val_acc: 0.6890
Epoch 10/10
13934/13934 [==============================] - 9s - loss: 0.7001 - acc: 0.6940 - val_loss: 0.7226 - val_acc: 0.6885
_________________________________________________________________
Layer (type)                 Output Shape              Param #   
=================================================================
input_6 (InputLayer)         (None, 32, 32, 3)         0         
_________________________________________________________________
conv2d_6 (Conv2D)            (None, 28, 28, 10)        760       
_________________________________________________________________
max_pooling2d_6 (MaxPooling2 (None, 14, 14, 10)        0         
_________________________________________________________________
flatten_6 (Flatten)          (None, 1960)              0         
_________________________________________________________________
dense_6 (Dense)              (None, 3)                 5883      
=================================================================
Total params: 6,643
Trainable params: 6,643
Non-trainable params: 0
_________________________________________________________________


optimize2 增加神经网络的层数


我们在模型中多添加几层并且提高卷几层的输出维度,这次结果得到显著提升:0.750904


#参数初始化
filters1=50
filters2=100
filters3=100
filtersize=(5,5)
epochs =10
batchsize=128
input_shape=(32,32,3)


from keras.models import Sequential
model = Sequential()
model.add(keras.layers.InputLayer(input_shape=input_shape))
model.add(keras.layers.convolutional.Conv2D(filters1, filtersize, strides=(1, 1), padding='valid', data_format="channels_last", activation='relu'))
model.add(keras.layers.MaxPooling2D(pool_size=(2, 2)))
model.add(keras.layers.convolutional.Conv2D(filters2, filtersize, strides=(1, 1), padding='valid', data_format="channels_last", activation='relu'))
model.add(keras.layers.MaxPooling2D(pool_size=(2, 2)))
model.add(keras.layers.convolutional.Conv2D(filters3, filtersize, strides=(1, 1), padding='valid', data_format="channels_last", activation='relu'))
model.add(keras.layers.Flatten())
model.add(keras.layers.Dense(units=3, input_dim=50,activation='softmax'))
model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])
model.fit(train_x, train_y, epochs=epochs, batch_size=batchsize,validation_split=0.3)
model.summary()


Train on 13934 samples, validate on 5972 samples
Epoch 1/10
13934/13934 [==============================] - 44s - loss: 0.8613 - acc: 0.5985 - val_loss: 0.7778 - val_acc: 0.6586
Epoch 2/10
13934/13934 [==============================] - 44s - loss: 0.7493 - acc: 0.6697 - val_loss: 0.7545 - val_acc: 0.6808
Epoch 3/10
13934/13934 [==============================] - 43s - loss: 0.7079 - acc: 0.6877 - val_loss: 0.7150 - val_acc: 0.6947
Epoch 4/10
13934/13934 [==============================] - 43s - loss: 0.6694 - acc: 0.7061 - val_loss: 0.6496 - val_acc: 0.7261
Epoch 5/10
13934/13934 [==============================] - 43s - loss: 0.6274 - acc: 0.7295 - val_loss: 0.6683 - val_acc: 0.7125
Epoch 6/10
13934/13934 [==============================] - 43s - loss: 0.5950 - acc: 0.7462 - val_loss: 0.6194 - val_acc: 0.7400
Epoch 7/10
13934/13934 [==============================] - 43s - loss: 0.5562 - acc: 0.7655 - val_loss: 0.5981 - val_acc: 0.7465
Epoch 8/10
13934/13934 [==============================] - 43s - loss: 0.5165 - acc: 0.7852 - val_loss: 0.6458 - val_acc: 0.7354
Epoch 9/10
13934/13934 [==============================] - 46s - loss: 0.4826 - acc: 0.7986 - val_loss: 0.6206 - val_acc: 0.7467
Epoch 10/10
13934/13934 [==============================] - 45s - loss: 0.4530 - acc: 0.8130 - val_loss: 0.5984 - val_acc: 0.7569
_________________________________________________________________
Layer (type)                 Output Shape              Param #   
=================================================================
input_15 (InputLayer)        (None, 32, 32, 3)         0         
_________________________________________________________________
conv2d_31 (Conv2D)           (None, 28, 28, 50)        3800      
_________________________________________________________________
max_pooling2d_23 (MaxPooling (None, 14, 14, 50)        0         
_________________________________________________________________
conv2d_32 (Conv2D)           (None, 10, 10, 100)       125100    
_________________________________________________________________
max_pooling2d_24 (MaxPooling (None, 5, 5, 100)         0         
_________________________________________________________________
conv2d_33 (Conv2D)           (None, 1, 1, 100)         250100    
_________________________________________________________________
flatten_15 (Flatten)         (None, 100)               0         
_________________________________________________________________
dense_7 (Dense)              (None, 3)                 303       
=================================================================
Total params: 379,303
Trainable params: 379,303
Non-trainable params: 0
_________________________________________________________________


输出结果


pred=model.predict_classes(test_x)
pred=lb.inverse_transform(pred)
print(pred)
test['Class']=pred
test.to_csv('sub02.csv',index=False)


6636/6636 [==============================] - 7s     
['MIDDLE' 'YOUNG' 'MIDDLE' ..., 'MIDDLE' 'MIDDLE' 'YOUNG']


i = random.choice(train.index)
img_name = train.ID[i]
img=Image.open(os.path.join(root_dir,'Train',img_name))
img.show()
pred = model.predict_classes(train_x)
print('Original:', train.Class[i], 'Predicted:', lb.inverse_transform(pred[i]))


19872/19906 [============================>.] - ETA: 0sOriginal: MIDDLE Predicted: MIDDLE


结果


40.png

image.png

还可以优化,继续探讨



相关实践学习
SLB负载均衡实践
本场景通过使用阿里云负载均衡 SLB 以及对负载均衡 SLB 后端服务器 ECS 的权重进行修改,快速解决服务器响应速度慢的问题
负载均衡入门与产品使用指南
负载均衡(Server Load Balancer)是对多台云服务器进行流量分发的负载均衡服务,可以通过流量分发扩展应用系统对外的服务能力,通过消除单点故障提升应用系统的可用性。 本课程主要介绍负载均衡的相关技术以及阿里云负载均衡产品的使用方法。
相关文章
|
2月前
|
机器学习/深度学习 人工智能 安全
探索AI的未来:从机器学习到深度学习
【10月更文挑战第28天】本文将带你走进AI的世界,从机器学习的基本概念到深度学习的复杂应用,我们将一起探索AI的未来。你将了解到AI如何改变我们的生活,以及它在未来可能带来的影响。无论你是AI专家还是初学者,这篇文章都将为你提供新的视角和思考。让我们一起探索AI的奥秘,看看它将如何塑造我们的未来。
87 3
|
1月前
|
机器学习/深度学习 人工智能 算法
探索机器学习:从线性回归到深度学习
本文将带领读者从基础的线性回归模型开始,逐步深入到复杂的深度学习网络。我们将通过代码示例,展示如何实现这些算法,并解释其背后的数学原理。无论你是初学者还是有经验的开发者,这篇文章都将为你提供有价值的见解和知识。让我们一起踏上这段激动人心的旅程吧!
|
23天前
|
机器学习/深度学习 人工智能 算法
机器学习与深度学习:差异解析
机器学习与深度学习作为两大核心技术,各自拥有独特的魅力和应用价值。尽管它们紧密相连,但两者之间存在着显著的区别。本文将从定义、技术、数据需求、应用领域、模型复杂度以及计算资源等多个维度,对机器学习与深度学习进行深入对比,帮助您更好地理解它们之间的差异。
|
2月前
|
机器学习/深度学习 数据采集 数据可视化
Python数据科学实战:从Pandas到机器学习
Python数据科学实战:从Pandas到机器学习
|
2月前
|
机器学习/深度学习 人工智能 算法
【手写数字识别】Python+深度学习+机器学习+人工智能+TensorFlow+算法模型
手写数字识别系统,使用Python作为主要开发语言,基于深度学习TensorFlow框架,搭建卷积神经网络算法。并通过对数据集进行训练,最后得到一个识别精度较高的模型。并基于Flask框架,开发网页端操作平台,实现用户上传一张图片识别其名称。
111 0
【手写数字识别】Python+深度学习+机器学习+人工智能+TensorFlow+算法模型
|
2月前
|
机器学习/深度学习 TensorFlow API
机器学习实战:TensorFlow在图像识别中的应用探索
【10月更文挑战第28天】随着深度学习技术的发展,图像识别取得了显著进步。TensorFlow作为Google开源的机器学习框架,凭借其强大的功能和灵活的API,在图像识别任务中广泛应用。本文通过实战案例,探讨TensorFlow在图像识别中的优势与挑战,展示如何使用TensorFlow构建和训练卷积神经网络(CNN),并评估模型的性能。尽管面临学习曲线和资源消耗等挑战,TensorFlow仍展现出广阔的应用前景。
81 5
|
2月前
|
机器学习/深度学习 人工智能 TensorFlow
基于TensorFlow的深度学习模型训练与优化实战
基于TensorFlow的深度学习模型训练与优化实战
111 0
|
2月前
|
机器学习/深度学习 数据采集 人工智能
机器学习入门:Python与scikit-learn实战
机器学习入门:Python与scikit-learn实战
73 0
|
2月前
|
机器学习/深度学习 自然语言处理 语音技术
探索机器学习中的深度学习模型:原理与应用
探索机器学习中的深度学习模型:原理与应用
47 0
|
3月前
|
数据采集 机器学习/深度学习 TensorFlow
声纹识别实战:从数据采集到模型训练
【10月更文挑战第16天】声纹识别技术通过分析个人的语音特征来验证其身份,具有无接触、便捷的特点。本文将带你从零开始,一步步完成声纹识别系统的构建,包括数据采集、音频预处理、特征提取、模型训练及评估等关键步骤。我们将使用Python语言和相关的科学计算库来进行实践。
505 0