numpy 1.9.0:ValueError:概率总和不等于 1

Posted

技术标签:

【中文标题】numpy 1.9.0:ValueError:概率总和不等于 1【英文标题】:numpy 1.9.0: ValueError: probabilities do not sum to 1 【发布时间】:2014-11-17 01:42:00 【问题描述】:

我有一个大代码,它在某一时刻根据从 probability density function (PDF) 中获取的概率对数组中的值进行采样。

为此,我使用了numpy.random.choice,它在numpy 1.8.0 之前工作得很好。这是一个MWE(文件pdf_probs.txt可以下载here):

import simplejson
import numpy as np

# Read probabilities from file.
f = open('pdf_probs.txt', 'r')
probs = simplejson.load(f)
f.close()

print sum(probs)  # <-- Not *exactly* 1. but very close: 1.00000173042
# Define array.
arr = np.linspace(1., 100., len(probs))

# Get samples using the probabilities in probs.
samples = np.random.choice(arr, size=1000, replace=True, p=probs)

问题是在使用numpy 1.9.0 测试后,上面的代码失败并出现错误:

Traceback (most recent call last):
  File "numpy_180_vs_190_np_random_choice.py", line 13, in <module>
    samples = np.random.choice(arr, size=1000, replace=True, p=probs)
  File "mtrand.pyx", line 1083, in mtrand.RandomState.choice (numpy/random/mtrand/mtrand.c:10106)
ValueError: probabilities do not sum to 1

鉴于使用非常小的浮点数时出现的小偏差,PDF 概率的总和不会恰好 1。

据我所知,以前版本的numpy (1.8.0) 显然比新版本的1.9.0 具有更大的容差,但我可能是错的。

为什么这适用于numpy 1.8.0 而不适用于1.9.0?如何使我的代码与新的 1.9.0 版本一起使用?

【问题讨论】:

以下是对容差测试的更改:1.9 version vs 1.8 version。 【参考方案1】:

我认为 1.7e-6 是一个足够大的相对错误,值得抱怨。但是,如果您确信错误可以忽略不计,则可以很容易地重新规范化:

>>> probs = np.array(probs)
>>> probs /= probs.sum()
>>> probs.sum()
1.0
>>> samples = np.random.choice(arr, size=1000, replace=True, p=probs)
>>> samples[:5]
array([  1.37635054,   1.1287515 ,   1.7229892 ,  19.8967587 ,   2.07953181])

【讨论】:

感谢@DSM,这是一个我没有想到的非常简单的解决方案。您知道从1.8.0 更改为1.9.0 导致代码不再工作的原因吗? 这对我不起作用,我的概率是大整数。当我完成这一步 robs /= probs.sum() 时,它只会创建一个 0 数组,所以我的 sum() 为零 @jrubins 这是整数除法的结果。如果你做probs /= probs.sum().astype(float),你应该没问题。 只是给仍然遇到问题的人的说明。与上面类似,将源数组的数据类型(dtype)设置为np.float64,而不是32bit float,显然也不是int。使用 32 位浮点数,在标准化(除以总和)时可能会出现 1e-7 的错误。这是一个大到足以导致 numpy 引发异常的错误。 对于嵌套数组,如np.array([[0.4, 0.5], [0.3, 0.7]]),必须使用轴来正确广播和计算它:probs /= probs.sum(axis=1).astype(float)[:, np.newaxis] 我只是想添加这个,因为我必须搜索和测试更多让它在我的代码中工作。

以上是关于numpy 1.9.0:ValueError:概率总和不等于 1的主要内容,如果未能解决你的问题,请参考以下文章

ValueError:使用序列python,numpy设置数组元素[重复]

ValueError: X 必须是 NumPy 数组

Numpy、Pandas 和 Sklearn 中的多维缩放拟合(ValueError)

无法导入 scikit-learn - ValueError:numpy.dtype 的大小错误,

“ValueError:无法将 NumPy 数组转换为张量(不支持的对象类型 numpy.ndarray)。在 TensorFlow CNN 中进行图像分类

ValueError:找到暗淡3的数组。估计器预期<= 2。使用numpy数组时