【问题标题】:Python: Frequency of occurrencesPython:出现频率
【发布时间】:2014-03-02 12:51:35
【问题描述】:

我有整数列表,想获取每个整数的频率。这是讨论here

问题是当我的数据集仅包含整数时,我使用的方法给了我浮点数的频率。为什么会发生这种情况以及如何从数据中获取整数频率?

我正在使用 pyplot.histogram 绘制具有出现频率的直方图

import numpy as np
import matplotlib.pyplot as plt
from numpy import *
data = loadtxt('data.txt',dtype=int,usecols=(4,)) #loading 5th column of csv file into array named data. 
plt.hist(data) #plotting the column as histogram 

我正在获取直方图,但我注意到如果我“打印” hist(data)

hist=np.histogram(data)
print hist(data)

我明白了:

(array([ 2323, 16338,  1587,   212,    26,    14,     3,     2,     2,     2]), 
array([  1. ,   2.8,   4.6,   6.4,   8.2,  10. ,  11.8,  13.6,  15.4,
    17.2,  19. ]))

其中第二个数组表示值,第一个数组表示出现次数。

在我的数据集中,所有值都是整数,第二个数组有浮点数是如何发生的,我应该如何获得整数的频率?

更新:

这样就解决了问题,谢谢Lev的回复。

plt.hist(data, bins=np.arange(data.min(), data.max()+1))

为避免产生新问题,我如何为每个整数绘制“中间”列?比如说,我希望整数 3 的列在 2.5 和 3.5 之间而不是在 3 和 4 之间。

【问题讨论】:

  • 您确定您使用的是您认为的数据吗?您的评论说第 4 列,但索引从 0 开始,所以第 4 列实际上是第 5 列。
  • 是的,这是第五栏,错字。
  • 我猜应该是data.max() + 2np.arange 没有上边框,bins 包含范围(元素从 0-1、1-2、...)

标签: python matplotlib


【解决方案1】:

如果您不指定要使用的 bin,np.histogrampyplot.hist 将使用默认设置,即使用 10 个相等的 bin。第一个 bin 的左边界是最小值,最后一个 bin 的右边界是最大的。

这就是 bin 边界是浮点数的原因。您可以使用 bins 关键字参数来强制选择另一种垃圾箱,例如:

plt.hist(data, bins=np.arange(data.min(), data.max()+1))

编辑:将所有 bin 向左移动的最简单方法可能只是从所有 bin 边界中减去 0.5:

plt.hist(data, bins=np.arange(data.min(), data.max()+1)-0.5)

实现相同效果的另一种方法(如果存在非整数,则不等效):

plt.hist(data, bins=np.arange(data.min(), data.max()+1), align='left')

【讨论】:

  • 所以如果我知道不同值的确切数量,我可以将值放在括号中吗?如果我不知道,那么你的建议。我会试试的。
  • @user40 是的,您可以指定任何序列,但请记住,这是您提供的 borders,因此 n 个 bin 有 n+1 个。此外,AFAIK 的 bin 之间不能有“空间”,尽管您可以通过指定 bin 宽度使其看起来有一些空间。编辑:我刚刚意识到你说了一些不同的话。是的,您可以只指定一个数字,例如 10。这意味着相同大小的 bin 的数量,从 min 到 max。
  • 成功了,谢谢。但是在图上,每个 bin 都取一个整数到下一个整数的完整值,我如何放置 bin,比如 value=2 的 1.5 到 2.5,3 的 2.5-3.5 等。我已经更新了我的问题。跨度>
  • @user40 从所有垃圾箱中减去 0.5 是否满足您的需求?见我上面的编辑
  • 你介意看看这个吗:stackoverflow.com/questions/22132298/…
【解决方案2】:

(迟到了,只是想我会添加一个seaborn 实现)

上述问题的Seaborn实现:

seaborn.__version__ = 0.9.0 在撰写本文时。

加载库并设置模拟数据。

import numpy as np
import matplotlib.pyplot as plt
import seaborn as sns

data = np.array([3]*10 + [5]*20 + [7]*5 + [9]*27 + [11]*2)

使用seaborn.distplot绘制数据:

使用指定的箱子,按上述问题计算。

sns.distplot(data,bins=np.arange(data.min(), data.max()+1),kde=False,hist_kws={"align" : "left"})
plt.show()

尝试numpy 内置分箱方法

我使用了下面的doane 分箱方法,它产生整数分箱,可能值得尝试numpy.histogram_bin_edges 中的standard binning methods,因为这是matplotlib.hist() 分箱数据的方式。

sns.distplot(data,bins="doane",kde=False,hist_kws={"align" : "left"})
plt.show()

生成以下直方图:

【讨论】:

    【解决方案3】:

    您可以从itertools 使用groupby,如How to count the frequency of the elements in a list? 所示

    import numpy as np
    from itertools import groupby
    freq = {key:len(list(group)) for key, group in groupby(np.sort(data))}
    

    【讨论】:

    • 啤酒花,@user40 你是对的,所以应该先排序。此外,将结果收集到字典中会很方便。代码已更新。
    猜你喜欢
    • 1970-01-01
    • 2020-02-29
    • 1970-01-01
    • 2020-06-01
    • 1970-01-01
    • 2023-03-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多