Image Classification#
下面我们研究多分类问题,问题描述如下:

给定一张图片,经过模型后输出一个向量,向量的维度等于类别数,每个元素表示该类别的概率,且所有元素的和为1
其实多分类的具体框架和二分类相似,都是先经过多个卷积层/池化层/激活函数,最后展开成一个向量,再经过MLP。不过最后的输出层不同,二分类输出一个元素,经过sigmoid函数得到概率;多分类输出一个向量,经过softmax函数得到每个分类的概率
Softmax函数#
Softmax函数的定义如下:
softmax(xi)=∑j=1neβxjeβxi
通常情况下β设置为1,当β→∞时,softmax趋近于argmax
Cross-Entropy Loss#
现在已经可以得到每个类别的概率,那我们该怎么计算损失函数呢
如果标签是one-hot编码的,那么仍然可以使用NLL损失函数,只需计算所属的类别的损失即可
L=−i=1∑nyilog(pi)
其中yi是标签的one-hot编码,pi是模型输出的概率(已经经过softmax函数)
但如果标签表示为图片属于某个类别的概率,那么我们需要一种标准来计算模型输出的概率分布和标签的概率分布之间的差异

KL散度:
KL散度是一种常用的计算两个概率分布之间差异的指标,定义如下:
DKL(P∣∣Q)=i=1∑nP(i)log(Q(i)P(i))
其中P和Q分别是两个概率分布,P(i)和Q(i)分别是第i个类别的概率
KL散度的几个特点:
- 不对称,即DKL(P∣∣Q)=DKL(Q∣∣P)
- DKL(P∣∣Q)≥0,当且仅当P=Q时,DKL(P∣∣Q)=0
把KL散度展开
DKL(P∣∣Q)=−i=1∑nP(i)log(Q(i))−(−i=1∑nP(i)log(P(i)))
其中−∑i=1nP(i)log(P(i))表示P的熵,即H(P),−∑i=1nP(i)log(Q(i))表示交叉熵,即H(P,Q),因此KL散度可以表示为:
DKL(P∣∣Q)=H(P,Q)−H(P)
P是固定的,H(P)是常数,因此最小化KL散度等价于最小化交叉熵H(P,Q)
我们得到了交叉熵损失函数的定义:
L=−i=1∑nP(i)log(Q(i))
Underfitting#
Underfitting最简单的解决方法就是增加模型的容量,比如增加模型层数,增加参数数量
但增加模型容量可能会破坏参数的分布,导致模型难以优化(比如同一学习率对于不同层的参数可能不合适),我们需要一些方法来使模型深度增加后仍然能进行可控的优化
Batch Normalization#
为了控制不同层之间参数分布变化,一般会在FC Layer后,激活函数前加入Batch Normalization层
下面我们看一下BatchNorm的实现:
设输入X的维度为N×D,其中N是batch size,D是特征维度
- 计算输入的均值和方差
μ=N1i=1∑NXi,σ2=N1i=1∑N(Xi−μ)2
其中Xi表示第i个样本的特征向量,μ和σ2都是D维的向量
- 对输入进行Normalize
X^i=σ2+ϵXi−μ
ϵ是一个小常数,防止除以0
这样得到了一个方差1、均值0的分布,但我们希望模型能够学习到不同的分布,因此需要进行缩放和平移
- 进行缩放和平移
Yi=γX^i+β
其中γ和β是可学习的参数,分别控制缩放和平移的程度。在反向传播时像线性层一样更新

经过BatchNorm层之后,输入被转化为一个方差为γ2、均值为β的分布
summary:
- 前向传播时要计算μ和σ2,用moving average来更新μrms和σrms2
- 反向传播时要更新γ和β
- 在输出层(Softmax之前)不应再加入batchnorm层,否则会破坏参数分布
- 在Batch较小时,由于μ和σ2的估计不准确,会导致效果变差
- 测试时使用的μ和σ2与训练时的来源并不一样,可能导致结果不稳定