softmax函数

softmax函数

image-20220401204312175

softmax函数如下
f ( x ) i = e x i ∑ j = 1 n e x j , j = 1 , 2 , … , n f(x)_{i}=\frac{e^{x_{i}}}{\sum_{j=1}^{n} e^{x_{j}}}, j=1,2, \ldots, n f(x)i=j=1nexjexi,j=1,2,,n

softmax上溢出(overflow)和下溢出(underflow)问题

  • c 极其大,导致分子计算 e c e^c ec时上溢出。
  • c 为负数,且 |c|很大,此时分母是一个极小的正数,有可能四舍五入为0,导致下溢出。
解决方案

​ 令$ M = max(x_i), i =1,2,3,….,n , 即 M 为 所 有 ,即M为所有 ,Mx_i 中 最 大 的 值 , 那 么 我 们 只 需 要 计 算 中最大的值,那么我们只需要计算 f(x_i - M) 的 值 , 就 可 以 解 决 上 溢 出 、 下 溢 出 的 问 题 了 , 并 且 , 计 算 结 果 理 论 上 仍 然 和 的值,就可以解决上溢出、下溢出的问题了,并且,计算结果理论上仍然和 f(x_i)$保持一致。

image-20220401204941323

​ 其中M=3是z1,z2,z3中的最大值。可见计算结果并未改变。
​ 通过这样的变换,对任何一个 x i x_i xi,减去M之后,e的指数的最大值为0,所以不会发生上溢出;同时,分母中也至少会包含一个值为1的项,所以分母也不会下溢出(四舍五入为0)。

分子下溢出

​ 仍然有一个问题:如果softmax函数中的分子发生下溢出,也就是前面所说的 c 为负数,且 |c|很大,此时分母是一个极小的正数,有可能四舍五入为0的情况,此时,如果我们把softmax函数的计算结果再拿去计算 log,即 log softmax,其实就相当于计算 log(0),所以会得到 −∞,但这实际上是错误的,因为它是由舍入误差造成的计算错误。
l e f t log ⁡ [ f ( x i ) ] = log ⁡ ( e x i e x 1 + e x 2 + ⋯ e x n ) = log ⁡ ( e x i e M e x 1 e M + e x 2 e M + ⋯ e x n e M ) = log ⁡ ( e ( x i − M ) ∑ j n e ( x j − M ) ) = log ⁡ ( e ( x i − M ) ) − log ⁡ ( ∑ j n e ( x j − M ) ) {left} \log \left[f\left(x_{i}\right)\right]=\log \left(\frac{e^{x_{i}}}{e^{x_{1}}+e^{x_{2}}+\cdots e^{x_{n}}}\right)\\ =\log \left(\frac{\frac{e^{x_{i}}}{e^{M}}}{\frac{e^{x_{1}}}{e^{M}}+\frac{e^{x_{2}}}{e^{M}}+\cdots \frac{e^{x_{n}}}{e^{M}}}\right)= \log \left( \frac{e^{\left(x_{i}-M\right)}}{\sum_{j}^{n} e^{\left(x_{j}-M\right)}}\right) \\=\log \left(e^{\left(x_{i}-M\right)}\right)-\log \left(\sum_{j}^{n} e^{\left(x_{j}-M\right)}\right) leftlog[f(xi)]=log(ex1+ex2+exnexi)=log(eMex1+eMex2+eMexneMexi)=log(jne(xjM)e(xiM))=log(e(xiM))log(jne(xjM)) {left}
会产生下溢出的因素已经被消除掉了——求和项中,至少有一项的值为1,这使得log后面的值不会下溢出,也就不会发生计算 log(0) 的悲剧。

nn.log_softmax

​ 对于单标签多分类问题,直接经过softmax求出概率分布,然后把这个概率分布用crossentropy做一个似然估计误差。但是softmax求出来的概率分布,每一个概率都是(0,1)的,这就会导致有些概率过小,导致下溢。
​ 考虑到这个概率分布总归是要经过crossentropy的,而crossentropy的计算是把概率分布外面套一个-log 来似然,那么直接在计算概率分布的时候加上log,把概率从(0,1)变为(-∞,0),这样就防止中间会有下溢出。
​ 所以log_softmax说白了就是将本来应该由crossentropy做的套log的工作提到预测概率分布来,跳过了中间的存储步骤,防止中间数值会有下溢出,使得数据更加稳定。
​ 正是由于把log这一步从计算误差提到前面,所以用log_softmax之后,下游的计算误差的function就应该变成NLLLoss(它没有套log这一步,直接将输入取反,然后计算和label的乘积求和平均)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

simpsun

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值