分布度量
信息量
假设
可以理解为,一个事件发生的概率越大,则它所携带的信息量就越小,而当
举个例子,小明平时不爱学习,考试经常不及格,而小王是个勤奋学习的好学生,经常得满分,所以我们可以做如下假设:
事件 A:小明考试及格,对应的概率
熵
那么什么又是熵呢?还是通过上边的例子来说明,假设小明的考试结果是一个 0-1 分布。
对应小王的熵:
虽然小明考试结果的不确定性较低,毕竟十次有 9 次都不及格,但是也比不上小王(1000 次考试只有一次才可能不及格,结果相当的确定)。我们再假设一个成绩相对普通的学生小东,他及格的概率是
其熵为 1,他的不确定性比前边两位同学要高很多,在成绩公布之前,很难准确猜测出他的考试结果。
熵其实是信息量的期望值,它是一个随机变量的确定性的度量。熵越大,变量的取值越不确定,反之就越确定。
对于一个随机变量
的值在 0-1 之间,取对数后小于零
如果
为了保证有效性,这里约定当
当
可以看出,当两种取值的可能性相等时,不确定度最大(此时没有任何先验知识),这个结论可以推广到多种取值的情况。在图中也可以看出,当
互信息 (Mutual Information)
无监督学习中常用的损失函数,作用于标签时,最大化预测标签和真实标签的信息熵,可以促使预测标签 certain 且 diverse,
直观地说,如果把熵
KL 散度
相对熵(relative entropy)又称为 KL 散度(Kullback-Leibler divergence),KL 距离,是两个随机分布间距离的度量。记为
某个随机变量的编码长度怎么算?
首先要知道什么是编码长度,这个其实很简单的,比如我们有一个数字
你看概率越大的
平均编码长度怎么算?
如果根据每个
如果我们搞错情况了,以为
于是就会基于错误的分布
KL散度怎么算
霍夫曼编码是最优编码,但如果你对
也就是:
这就是KL散度
所以KL散度其实是利用最优编码这个代理量去衡量两个分布之间有多大的区别。
对了,为什么是比特数,因为霍夫曼是二叉树,左0右1,故为比特
以上摘自 KL散度衡量的是两个概率分布的距离吗? (opens new window) 刘斯坦回答部分
数学推导
并且为了保证连续性,做如下约定:
显然,当
上式最后的
基于此,相对熵的意义就很明确了:
注意:
如果继续用 2 为底的对数计算,则 KL 散度值表示信息损失的二进制位数。
如果
和 是同分布的,则 KL 散度为 0。 KL散度不是距离,因为不符合对称性,所以用 KL 散度度量分布差异时需设计成对称的,
Specializing to Gaussian measures and , then the KL divergence is given by
条件熵 (Conditional Entropy)
条件熵是在已知随机变量
最小化条件熵让模型远离决策边界,可以应用在无监督数据上,以利用其数据分布信息。
JS 散度(Jensen-Shannon)
JS 散度度量了两个概率分布的相似度,基于 KL 散度的变体,解决了 KL 散度非对称的问题。一般地,JS 散度是对称的,其取值是 0 到 1 之间。定义如下:
KL 散度和 JS 散度度量的时候有一个问题: 如果两个分布 p, q 离得很远,完全没有重叠的时候,那么 KL 散度值是没有意义的,而 JS 散度值是一个常数。这在学习算法中是比较致命的,这就意味这这一点的梯度为 0,梯度消失了。
Maximum Mean Discrepancy (MMD)
定义和特点:
MMD是通过比较两个分布的样本均值的差异来衡量它们之间的距离。具体地,它通过特征空间中的核函数来度量分布之间的差异,通常使用正定核如高斯核。
优点:
简单直观,易于实现和计算。 在一些实验中表现良好,特别是当分布差异较为显著时效果较好。
缺点:
对于高维和复杂的数据分布,可能会出现较高的误差。 对于较小的样本量可能表现不稳定。
适用条件:
适合用于比较较为简单的数据分布和特征空间。 在计算资源有限的情况下表现较为出色。
代码
MMD 是通过核方法来度量两个分布之间的距离,这里以高斯核为例实现 MMD 的计算:
import numpy as np
def gaussian_kernel(x, y, sigma=1.0):
return np.exp(-np.linalg.norm(x - y)**2 / (2 (sigma *2)))
def mmd(X, Y, kernel=gaussian_kernel):
m = len(X)
n = len(Y)
K_xx = np.zeros((m, m))
K_yy = np.zeros((n, n))
K_xy = np.zeros((m, n))
for i in range(m):
for j in range(m):
K_xx[i, j] = kernel(X[i], X[j])
for i in range(n):
for j in range(n):
K_yy[i, j] = kernel(Y[i], Y[j])
for i in range(m):
for j in range(n):
K_xy[i, j] = kernel(X[i], Y[j])
return np.mean(K_xx) + np.mean(K_yy) - 2 np.mean(K_xy)
# Example usage:
X = np.random.randn(100, 2) # Sample from distribution X
Y = np.random.randn(100, 2) # Sample from distribution Y
distance_mmd = mmd(X, Y)
print(f"MMD distance between X and Y: {distance_mmd}")
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
30
31
32
33
34
Correlation Alignment (CORAL)
定义和特点:
CORAL通过最小化两个分布之间的协方差矩阵的差异来进行域自适应。它试图通过特征之间的协方差来对齐两个域的特征分布。
优点:
考虑了特征之间的相关性,能够更加准确地度量分布的差异。 对于特征之间存在较强关联的数据集有较好的适应性。
缺点:
受限于协方差矩阵的计算,当特征空间较大时可能计算代价较高。 只考虑了二阶统计量,可能忽略了高阶的分布差异。
适用条件:
适合于特征之间具有较强相关性的数据集。 对于计算资源充足的情况下,可以有效地对齐分布。
代码
CORAL 通过最小化协方差矩阵的差异来进行域自适应:
from sklearn.covariance import LedoitWolf
def coral(X, Y):
cov_X = LedoitWolf().fit(X).covariance_
cov_Y = LedoitWolf().fit(Y).covariance_
return np.linalg.norm(cov_X - cov_Y)
# Example usage:
X = np.random.randn(100, 2) # Sample from distribution X
Y = np.random.randn(100, 2) # Sample from distribution Y
distance_coral = coral(X, Y)
print(f"CORAL distance between X and Y: {distance_coral}")
2
3
4
5
6
7
8
9
10
11
12
13
14
15
Central Moment Discrepancy (CMD)
定义和特点:
CMD通过比较高阶中心矩来度量两个分布之间的差异。它不仅考虑了均值和方差,还考虑了数据分布的更高阶统计信息。
优点:
能够更全面地捕捉数据分布的差异,尤其是对于非高斯分布和高阶统计信息的敏感性较好。
缺点:
需要计算和比较高阶统计量,计算复杂度可能较高。 对于样本量较少时,估计高阶统计量的稳定性可能较差。
适用条件:
适合用于捕捉高阶统计信息对分布差异影响显著的情况。 当数据分布复杂且不服从正态分布时表现较为突出。
代码
CMD 通过比较高阶中心矩来度量两个分布之间的差异,这里演示计算方差和偏度的差异:
from scipy.stats import moment
def cmd(X, Y):
var_X = np.var(X)
var_Y = np.var(Y)
skew_X = moment(X, moment=3)
skew_Y = moment(Y, moment=3)
return np.abs(var_X - var_Y) + np.abs(skew_X - skew_Y)
# Example usage:
X = np.random.randn(100) # Sample from distribution X
Y = np.random.randn(100) # Sample from distribution Y
distance_cmd = cmd(X, Y)
print(f"CMD distance between X and Y: {distance_cmd}")
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
Maximum Density Divergence (MDD)
定义和特点:
MDD通过比较两个分布的密度函数的差异来度量它们之间的距离。通常使用KL散度来作为分布差异的度量标准。
优点:
直接基于密度函数比较,能够较为准确地捕捉分布之间的差异。 在分布有明显差异时效果较好。
缺点:
对于高维和复杂分布的密度估计可能存在困难。 KL散度可能会受到样本稀疏性的影响。
适用条件:
适合用于直接比较密度函数的场景。 当能够准确估计密度函数时表现较为优越。
代码
MDD 通过比较两个分布的密度函数的差异来
from scipy.stats import entropy
from sklearn.neighbors import KernelDensity
def mdd(X, Y):
kde_X = KernelDensity(bandwidth=0.5).fit(X[:, np.newaxis])
kde_Y = KernelDensity(bandwidth=0.5).fit(Y[:, np.newaxis])
log_dens_X = kde_X.score_samples(X[:, np.newaxis])
log_dens_Y = kde_Y.score_samples(Y[:, np.newaxis])
return entropy(np.exp(log_dens_X), np.exp(log_dens_Y))
# Example usage:
X = np.random.randn(100) # Sample from distribution X
Y = np.random.randn(100) # Sample from distribution Y
distance_mdd = mdd(X, Y)
print(f"MDD distance between X and Y: {distance_mdd}")
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18