Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/320.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 互信息的香农熵_Python_Math_Entropy - Fatal编程技术网

Python 互信息的香农熵

Python 互信息的香农熵,python,math,entropy,Python,Math,Entropy,我有一些关于某些属性的统计数据,如: 1st iter : p1:10 p2:0 p3:12 p4:33 p5:0.17 p6:ok p8:133 p9:89 2nd iter : p1:43 p2:1 p6:ok p8:12 p9:33 3rd iter : p1:14 p2:0 p3:33 p5:0.13 p9:2 ... (p1 -> number of tries, p2 -> try done well, p3..pN -> properties of try).

我有一些关于某些属性的统计数据,如:

1st iter : p1:10 p2:0 p3:12 p4:33 p5:0.17 p6:ok p8:133 p9:89
2nd iter : p1:43 p2:1 p6:ok p8:12 p9:33
3rd iter : p1:14 p2:0 p3:33 p5:0.13 p9:2
...

(p1 -> number of tries, p2 -> try done well, p3..pN -> properties of try).
我需要计算每个属性的信息量。 经过一些量化过程(例如,到10个级别)以使所有输入数字处于同一级别后,输入文件开始显示如下:

p0: 4 3 2 4 5 5 6 7
p3: 4 5 3 3   
p4: 5 3 3 2 1 2 3 
...
其中
p(0)=函数(p1,p2)


不是每一个输入行都得到每一个
pK
,所以
len(pK)我假设您想要计算每个
p1
和每个
p2
p3
,。。。后来

1) 用以下公式计算p1的熵
H(X)

每个
x
都是
p1
的后续元素

2) 用相同的方程式计算
H(Y)
作为
pK
的熵,每个
x
都是
p1

3) 从
p1
pK
中创建一个新的配对集合:

pairs = zip(p1, pK)
请注意,如果数据列中的值具有不同的含义,则可能应该填充缺少的数据(例如使用
0
s或上一次迭代中的值)

4) 使用以下公式计算关节熵
H(X,Y)

请注意,您不能仅使用第一个等式并将每一对视为单个元素-您必须迭代该等式中
p1
pK
之间的整个笛卡尔积,使用
集合计算概率。因此,要迭代整个笛卡尔积,请在itertools.product(p1,pK)中对xy使用
:…

5) 然后您可以将
p1
pK
之间的互信息设置为:

使用numpy功能,您可以计算关节熵,如下所示:

其中
如果p>0
与:

对于某些i,在p(xi)=0的情况下,相应的和0 logb(0)的值被取为0

如果您不想使用
numpy
,那么没有它的版本可能看起来像:

def entropyPart(p):
    if not p:
        return 0

    return -p * math.log(p)

def entropy(X, Y):
    pairs = zip(X, Y)
    probs = []
    for pair in itertools.product(X,Y):
        probs.append(1.0 * sum([p == pair for p in pairs]) / len(pairs))

   return sum([entropyPart(p) for p in probs])

从维基百科文章的正式定义一节中取公式。他们称之为信息增益,但与互信息相同。为了计算包含在这个公式中的样本的熵,从维基百科文章的定义部分取公式

所以,你首先计算整个数据集的熵,然后从中减去熵,当你知道所讨论的心房安非他命的值时,剩下的熵


多维直方图可以在Python中使用
numpy.historogramdd()

计算哪两个量之间的互信息?主要目标是通过从列表中删除低信息属性来增加F=p1/p2(如果p2=0:F=F0)。那么它是关于pK和p1(p2)的吗@康斯坦丁我还不清楚。您有一组
N
样本,每个样本由9个元素/属性组成。您正在计算每个属性的熵。好的现在你要计算互信息。在什么和什么之间???@Konstantin其
I(p0,pK)
对于每个
pK
,结果是否与上述方法相同?好的,那么您的主要问题是您不知道所有样本的所有属性。当计算p0和pk之间的互信息时,只使用那些包含pk的样本。那么我每次都应该使用不同的
p0
,并且它们总是相同的长度。这听起来是合法的。美好的但似乎我需要记录一半的工作才能知道
p0
中的样本包含
pk
。但无论如何,谢谢。为什么不一样呢?我知道p0是p1和p2的函数,它们总是存在的,对吗?当计算p0和pk之间的MI时,您不需要其他属性,因此您的计算将始终基于两个向量,p0和pk。正如我所理解的:对于联合熵,我应该只考虑受pk影响的p0元素,因此len(pk)=len(p0'),其中p0'是p0的子数组
def entropy(X, Y):
    probs = []
    for c1 in set(X):
        for c2 in set(Y):
            probs.append(np.mean(np.logical_and(X == c1, Y == c2)))

    return np.sum(-p * np.log2(p) for p in probs if p > 0)
def entropyPart(p):
    if not p:
        return 0

    return -p * math.log(p)

def entropy(X, Y):
    pairs = zip(X, Y)
    probs = []
    for pair in itertools.product(X,Y):
        probs.append(1.0 * sum([p == pair for p in pairs]) / len(pairs))

   return sum([entropyPart(p) for p in probs])