在学习了python中的一些机器学习的相关模块后,再一次开始了深度学习之旅。不过与上次的TensorFlow框架不同,这一次接触的是fast.ai这样一个东西。这个框架还不稳定,网上也没有相关的中文文档。唯一一个学习站点就是 fastai 这样一个论坛,另外就是里面的公开课程。
性别识别模型使用体验: http://www.ctsch.cn/?page_id=11
请确认上传的图片中有人,否则对于其他类型的图片,也就当男女论处,目前在它的世界中只有男女。
附上fastai项目的相关连接:
- Github项目地址: https://github.com/fastai/fastai
- fastai论坛: http://forums.fast.ai/
- fastai课程:http://course.fast.ai/lessons/lesson1.html
注意:
- 在配置环境时使用 Anaconda,安装方法可以自行百度
- 使用安装fastai训练模型时要安装GPU版本(前提是你有支持GPU的显卡),否则建议你不要用来训练模型,使用cpu训练会非常非常慢。当然GPU需要安装cuda和cudnn(安装步骤可以自行百度)。
Github上有相关的安装教程,能够成功安装,有问题可以在本文后留言,我会尽力回复。
在该课程的第一课就是一个利用神经网络识别猫狗。在这中间使用了resnet34模型进行训练。这个模型是在ImageNet数据集比赛上获得过优异成绩的模型,这个预训练使我们不需要自己构建神经网络,只要我们能会使用就可以了。这也算是第一课的基础导入吧。
下面要讲的内容,在视频中都可以找到,这里主要写一些我觉的使用fastai比较重要和特殊的地方
|
1
2
3
4
5
6
|
# 在fastai要建立一个model,只需要下面的三行就可以了,第四行是训练model
# 使用model
# 图片数的组织类别
# 卷积神经网络的容器
# 训练model
|
- 要点一:训练、验证和预测数据的文件组织架构
图片数据的存放形式:
在每个分类(如:male、female)中存放的就是样本图片了。 -
要点二: 解释上面代码中的
learn.fit(0.01, 3):
我们现在使用的resnet34模型是一个在ImageNet数据集上训练好了的model,里面权重数据一个非常好了,不需要我们在进行改善什么,但我们需要根据我们自己的实际数据训练神经网络的最后一层权重。所以上面这个代码是训练model的最后一层。至于为什么,那是因为,resnet34预训练模型是使用ImageNet数据集训练的,他们的类别可能有1000类,所以模型的最后一层默认是1000维的,但是我们的数据分类只有两类—猫和狗。因此我们需要这一步骤。 -
要点三: fastai中ConvLearner类有一个自动寻找最优学习率的函数 learn.lr_fint()
我们知道,在神经网络中,学习率是一个非常重要的超参数,调节的不好,会导致模型不能收敛或者收敛的太慢。通过这个函数,它可以帮助我们在指定范围内自动找到最合适的学习率。我们可以通过learn.sched.plot_lr()函数绘制出学习率与训练轮数的关系;也可以通过learn.sched.plot()绘制出学习率与损失值得变化情况,从而选择出最合适的学习率。
以上是一些学习记录,下面开始训练性别识别模型。
使用resnet34训练性别识别模型
在训练之前首先要做的就是收集数据,数据是使用 GoogleImageDownloader 工具自动爬取的,在Google上爬了大概3500张图片,里面有些图片质量不够好,删除了之后大概还有2400张左右。
data and code url: 链接: https://pan.baidu.com/s/1TbvupSigvKJoQp8JrIFFOA 密码: sxqc
具体代码:
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
|
sys
os
np
pd
plt
)
import *
import *
import *
import *
import *
import *
import *
import *
'data/malefemale/'
224
# 使用resnet34model
resnet34
)
)
# 第一次轻微训练最后一层
)
)
|
在这一次的训练中,发现模型损失还有0.29,模型在验证上的正确率才到93%,模型还有优化的空间。
下面再一次构造模型并训练:
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
|
# 通过转变角度,增加样本
)
)
# 第一次训练最后一层,试探性
# 发现第一次训练有效果,在进一步训练
# 开启全部层都可以训练,对每层进行微训练
# 初步训练
)
# 发现上一次有效果,在进行深度训练
|
最后 模型在训练集上的loss到达了0.025,在验证集上的loss达到了0.18,在验证集上的正确率达到了 94.9%。在我多次训练后,发现这是最好的了,所以就没有再进行改进了。
但是,现在还没有完,我们现在要看看模型在数据集上的表现到底怎么样。下面,使用matplotlib库进行可视化分析:
可视化分析
首先获得模型的预测数据:
|
1
2
3
4
5
6
7
8
9
|
# 预测所有的验证集,返回的 ln pi的数据
# 将对数概率转回正常的概率
# 获取预测的分类,这里面是0,1数据,0表示女性,1表示男性
# 将所有的数据合并成pandas的DataFrame
# 输出下DataFrame
|
说明:
- image 图片样本的路径
- y_true 样本的真实类别
- y_pred 样本的预测类别
- y_prob_female 模型预测该样本为女性的概率
- y_prob_male 模型预测该样本为男性的概率
1、查看模型的混淆矩阵
|
1
2
3
4
5
6
|
confusion_matrix
sns
)
)
|
可以看到,在152个女性样本和143个男性样本中,有10张女性样本被错误的分成了男性,但仅有5个男性样本被错误的分词女性,可以看出模型在男性特征的学习中学习的较充足,到对女性特征学习还有待提高。出现这个情况的原因是在训练样本中男性样本比女多了近200个样本,因此模型学习男性的特征较多,因此判断更有把握。
2、查看模型在验证集中预测最有把握的样本
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
|
# 最有把握的女性
)
)
)
:
]
)
)
)
# 最有把握的男性
)
)
)
:
]
)
)
)
|
在这些样本中,男性和女性的外在特征都比较明显的显示出来了,因此模型的判断概率都是100%。
3、查看模型在验证集中预测错误最明显的的样本
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
|
# 预测出错最明显的女性
)
)
)
:
]
)
)
)
# 预测出错最明显的男性
)
)
)
:
]
)
)
)
|
从上面两幅图中可以看出,模型对于男女特征没有明显展示出来的样本(如马尾头发的样本)出错概率最大,另外从第一幅图的第四个样本看出,模型将具有肌肉的这样特征的样本认为是男性,这与我们生活中一般常识—–女性一般没有肌肉是吻合的。
在男性的错误样本中,我们可以看出模型在男性样本上的预测是很不错的。男性的第一个样本具有欺骗性,包括人类去识别可能也会出错,其他几个样本就是没有显示出男性特征,所以这个出错是可以容忍的。
总的来说,模型在预测时的表现是非常不错的,一般的有特征的图片都能正确识别,读者可以自行上传图片去试试。地址就在下面。
体验地址,上传图片就可以使用了。 http://www.ctsch.cn/?page_id=11