Cross Entropy 交叉熵是深度学习中经常使用的概念,用作损失函数评估目标和预测值之间的差异。
简介
在正式介绍交叉熵之前,先介绍一些基础概念。
信息量
从直观上来看,某个事件发生的概率越小其包含的信息量就越大,例如中国进入世界杯决赛和巴西进入世界杯决赛两个事件,显然前者的信息更多,为了评估这一特征,那么就引入了 $-log(x)$ 对数函数。
主要是该函数在 [0, 1]
这个概率区间内符合上述的描述,越逼近低概率其值越高,趋近于高概率的时候,对应值接近 0 。
熵
有了信息量的定义之后,熵就是所有信息量的期望,也就有如下公式。
$$ H(X) = -\sum_{i=1}^{n} {p(x_i) log(p(x_i))} $$
例如对于天气有如下的四种情况,晴 0.5、阴天 0.25、雨 0.15、雪 0.1 ,那么其对应的熵就是。
$$ \begin{align*} H(X) &= -\sum_{i=1}^{n} {p(x_i) log(p(x_i))} \ &= -0.5 \times log(0.5) - 0.25 \times log(0.25) - 0.15 \times log(0.15) - 0.1 \times log(0.1) \ &= 0.5 \times 0.69 + 0.25 \times 1.39 + 0.15 \times 1.90 + 0.1 \times 2.30 \ &= 1.21 \end{align*} $$
相对熵
也被称为 Kullback-Leibler Divergence, KL 散度,用来衡量两个概率分布 $P(x)$ 和 $Q(x)$ 的差异,在机器学习中,通常将前者作为真实分布,后者作为预测分布,希望通过一系列的训练使得 $Q$ 趋近于 $P$ 。
相对熵的计算公式如下。
$$ D_{KL}(p{\parallel}q) = \sum_{i=1}^{n}{p(x_i)log(\frac{p(x_i)}{q(x_i)})} $$
相对熵的值越小,意味着两者越接近。
交叉熵
将上述的公式进行转换。
$$ \begin{align*} D_{KL}(p{\parallel}q) &= \sum_{i=1}^{n}{p(x_i)log(\frac{p(x_i)}{q(x_i)})} \ &= \sum_{i=1}^{n} {p(x_i) log(p(x_i))} - \sum_{i=1}^{n} {p(x_i) log(q(x_i))} \ &= -H(p(x)) - \sum_{i=1}^{n} {p(x_i) log(q(x_i))} \end{align*} $$
上述的第一部分就是 $P$ 的熵,而后者则被称为交叉熵。
$$ H(p,q) = - \sum_{i=1}^{n} {p(x_i) log(q(x_i))} $$
在机器学习中,可以通过 KL 散度评估模型,而前者的熵不变,所以就直接使用交叉熵进行评估。
使用
在 Torch 中有 torch.nn
和 torch.nn.functional
两类实现,其中前者是对后者的封装,会保存一些参数。
torch.nn | torch.nn.functional |
---|---|
CrossEntroyLoss | cross_entropy |
LogSoftmax | log_softmax |
NLLLoss | nll_loss |
如下是简单示例。
import torch
torch.manual_seed(123)
inputs = torch.randn(3, 5)
target = torch.tensor([2, 4, 3])
print(torch.nn.functional.cross_entropy(inputs, target))
print(torch.nn.CrossEntropyLoss()(inputs, target))
其中输入的 Shape 为 (3, 5)
意味着有 3 个样本和 5 个分类,目标则是三个样本目标类序号,其计算方式类似如下。
probas = torch.softmax(inputs, dim=-1)
#print(probas.sum(dim=-1, keepdim=True))
target_probas = probas[[0, 1, 2], target]
logs = -torch.log(target_probas)
print(torch.mean(logs))