本文转载于其他博客,如有冒犯还望谅解!
1. 什么是logits?
说到Logits,首先要弄明白什么是Odds?
在英文里,Odds的本意是指几率、可能性。它和我们常说的概率又有什么区别呢?
在统计学里,概率(Probability)描述的是某事件A出现的次数与所有事件出现的次数之比:
P(A) = 发生事件A的次数 / 所有事件的次数。 (公式1)
很显然,概率 P是一个介于0到1之间的实数; P=0,表示事件A一定不会发生,而P=1,则表示事件A一定会发生。
以掷骰子为例,由于骰子为6面,任意一面上点数概率都是相同。所以,事件A:掷出点数为1的概率为:
对比而言,Odds指的是事件发生的概率与事件不发生的概率之比:
Odds(A)= 发生事件A的概率 / 不发生事件A的概率 (公式2)
还拿掷骰子的例子说事,掷出点数为1的Odds为:
很明显,Odds和概率之间的关系为:
进一步简化可知,
Odds(A)= 发生事件A次数 / 其他事件的次数(即不发生A的次数) (公式3)
换句话说,事件A的Odds 等于 事件A出现的次数 和 其它(非A)事件出现的次数 之比;
相比之下,事件A的概率 等于 事件A出现的次数 与 所有事件的次数 之比。
很容易推导得知:
概率P(A)和Odds(A)的值域是不同的。前者被锁定在[0,1]之间,而后者则是.
这说了半天,有何logit有什么关系呢?
请注意Logit一词的分解,对它(it)Log(取对数),这里“it”就是Odds。下面我们就可以给出Logit的定义了:
(公式4)
公式4实际上就是所谓Logit变换。
————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————————
tf.nn.softmax_cross_entropy_with_logits函数是TensorFlow中常用的求交叉熵的函数。其中函数名中的“logits”是个什么意思呢?它时不时地困惑初学者,下面我们就讨论一下。
-
tf.nn.softmax_cross_entropy_with_logits(
-
_sentinel=None,
-
labels=None,
-
logits=None,
-
dim=-1,
-
name=None
-
)
这个函数的功能就是计算labels和logits之间的交叉熵(cross entropy)。
第一个参数基本不用。此处不说明。
第二个参数label的含义就是一个分类标签,所不同的是,这个label是分类的概率,比如说[0.2,0.3,0.5],labels的每一行必须是一个概率分布。
现在来说明第三个参数logits,logit本身就是是一种函数,它把某个概率p从[0,1]映射到[-inf,+inf](即正负无穷区间)。这个函数的形式化描述为:logit=ln(p/(1-p))。
我们可以把logist理解为原生态的、未经缩放的,可视为一种未归一化的log 概率,如是[4, 1, -2]
于是,Softmax的工作则是,它把一个系列数从[-inf, +inf] 映射到[0,1],除此之外,它还把所有参与映射的值累计之和等于1,变成诸如[0.95, 0.05, 0]的概率向量。这样一来,经过Softmax加工的数据可以当做概率来用。
也就是说,logits是作为softmax的输入。经过softmax的加工,就变成“归一化”的概率(设为q),然后和labels代表的概率分布(设为q),于是,整个函数的功能就是前面的计算labels(概率分布p)和logits(概率分布q)之间的交叉熵
下面我们列举一个案例说明:
-
#!/usr/bin/env python3
-
# -*- coding: utf-8 -*-
-
"""
-
Created on Thu May 10 08:32:59 2018
-
@author: yhilly
-
"""
-
import tensorflow as tf
-
labels = [[0.2,0.3,0.5],
-
[0.1,0.6,0.3]]
-
logits = [[4,1,-2],
-
[0.1,1,3]]
-
logits_scaled = tf.nn.softmax(logits)
-
result = tf.nn.softmax_cross_entropy_with_logits(labels=labels, logits=logits)
-
with tf.Session() as sess:
-
print (sess.run(logits_scaled))
-
print (sess.run(result))
运行结果:
-
[[0.95033026 0.04731416 0.00235563]
-
[0.04622407 0.11369288 0.84008306]]
-
[3.9509459 1.6642545]
需要注意的是:
(1)如果labels的每一行是one-hot表示,也就是只有一个地方为1(或者说100%),其他地方为0(或者说0%),还可以使用tf.sparse_softmax_cross_entropy_with_logits()。之所以用100%和0%描述,就是让它看起来像一个概率分布。
(2)tf.nn.softmax_cross_entropy_with_logits()函数已经过时 (deprecated),它在TensorFlow未来的版本中将被去除。取而代之的是
tf.nn.softmax_cross_entropy_with_logits_v2()。
(3)参数labels,logits必须有相同的形状 [batch_size, num_classes] 和相同的类型(float16, float32, float64)中的一种,否则交叉熵无法计算。