float的标准化直方图:numpy / matplotlib中的意外行为

时间:2013-10-08 16:03:47

标签: python numpy matplotlib

所以,这是交易。我有一个介于0和1之间的大量浮点数。我想要一个浮点数组,它可以计算特定bin中有多少个实例。在单位间隔内有32个间隔均匀分布。

我认为一个标准的直方图可以做我想要的,但我得到一些令人费解的行为。基本上,标准化的直方图应该返回我想要的(我会想到),但它会抛出我在[0,1]之外的值。

>>> from numpy import *
>>> import matplotlib. pyplot as plt
>>> a = random.normal(0.4,0.1,1024)
>>> plt.hist(a, bins=32,range = ([0,1]),normed=True)
(array([ 0.     ,  0.     ,  0.0625 ,  0.03125,  0.15625,  0.40625,
        0.5    ,  1.     ,  2.0625 ,  2.     ,  3.125  ,  3.65625,
        3.78125,  4.3125 ,  3.3125 ,  2.59375,  1.8125 ,  1.40625,
        0.90625,  0.34375,  0.375  ,  0.0625 ,  0.0625 ,  0.03125,
        0.     ,  0.     ,  0.     ,  0.     ,  0.     ,  0.     ,
        0.     ,  0.     ]), array([ 0.     ,  0.03125,  0.0625 ,  0.09375,  0.125  ,  0.15625,
        0.1875 ,  0.21875,  0.25   ,  0.28125,  0.3125 ,  0.34375,
        0.375  ,  0.40625,  0.4375 ,  0.46875,  0.5    ,  0.53125,
        0.5625 ,  0.59375,  0.625  ,  0.65625,  0.6875 ,  0.71875,
        0.75   ,  0.78125,  0.8125 ,  0.84375,  0.875  ,  0.90625,
        0.9375 ,  0.96875,  1.     ]), <a list of 32 Patch objects>)
>>> histogram(a, bins=32,range = ([0,1]),density=True)
(array([ 0.     ,  0.     ,  0.0625 ,  0.03125,  0.15625,  0.40625,
        0.5    ,  1.     ,  2.0625 ,  2.     ,  3.125  ,  3.65625,
        3.78125,  4.3125 ,  3.3125 ,  2.59375,  1.8125 ,  1.40625,
        0.90625,  0.34375,  0.375  ,  0.0625 ,  0.0625 ,  0.03125,
        0.     ,  0.     ,  0.     ,  0.     ,  0.     ,  0.     ,
        0.     ,  0.     ]), array([ 0.     ,  0.03125,  0.0625 ,  0.09375,  0.125  ,  0.15625,
        0.1875 ,  0.21875,  0.25   ,  0.28125,  0.3125 ,  0.34375,
        0.375  ,  0.40625,  0.4375 ,  0.46875,  0.5    ,  0.53125,
        0.5625 ,  0.59375,  0.625  ,  0.65625,  0.6875 ,  0.71875,
        0.75   ,  0.78125,  0.8125 ,  0.84375,  0.875  ,  0.90625,
        0.9375 ,  0.96875,  1.     ]))

事实上,这种行为不只是小浮动。如果你使正态分布集中于7.4,并将范围移动到[7,8],你会得到同样令人费解的行为。

您使用numpy的{​​{1}}函数和histogram的{​​{1}}获得相同的行为。 (我认为这是前者的包装?排序?)

我做的事情是愚蠢的吗?这是一个错误吗?有没有更好的方法来创建表示近似数据的离散分布的数组?

1 个答案:

答案 0 :(得分:3)

  

我做的事情是愚蠢的吗?

嗯,是的,从某种意义上说,当某些事情令人困惑时没有阅读文档是愚蠢的,但说实话,我通常不会阅读文档,直到比我应该更晚,所以我不是很好扔石头的位置。 :^)

来自help(plt.hist)

normed : boolean, optional, default: False
    If `True`, the first element of the return tuple will
    be the counts normalized to form a probability density, i.e.,
    ``n/(len(x)`dbin)``, ie the integral of the histogram will sum to
    1. If *stacked* is also *True*, the sum of the histograms is
    normalized to 1.

基本上,规范化保证是什么

>>> a = np.random.normal(0.4,0.1,1024)
>>> n, bins, patches = plt.hist(a, bins=32,range = ([0,1]),normed=True)
>>> (np.diff(bins) * n).sum()
1.0