为什么 matplotlib 绘图和 seaborn 绘图中的计数值不同,而且都是错误的?
Why are the value of counts in the matplotlib plot and seaborn plot different, and both wrong?
所以我使用的数据集是来自 seaborn 的 tips。
我想针对 total_bill
列绘制直方图,我同时使用了 seaborn 和 matlotlib。
这是我的 matplotlib 直方图:
plt.hist(tips_df.total_bill);
这是我的 seaborn 直方图:
sns.histplot(tips_df.total_bill)
如您所见,在 total_bill
13 附近,频率似乎是最大的。
但是,在 matplotlib 中它大约是 68,而它在 seaborn 中大约是 48。
两者都是错误的。因为打字
tips_df["total_bill"].value_counts().sort_values(ascending=False).head(5)
我们得到输出
13.42 3
15.69 2
10.34 2
10.07 2
20.69 2
Name: total_bill, dtype: int64
我们可以看到,出现次数最多的是13左右,但是为什么y-axis上的计数值不对呢?
在直方图中,“矩形”的高度表示给定 范围 中有多少个值,而这又由矩形的宽度描述。您可以通过 (max - min) / number_of_rectangles.
得到每个矩形的宽度
例如,在 matplotlib 的输出中,有 10 个矩形(箱)。由于您的数据最小值约为 3,最大值约为 50,因此每个宽度约为 4.7 个单位宽。现在,为了获得第三个矩形范围,例如,我们从最小值开始并添加此宽度直到我们到达那里,即 3 + 4.7*2 = 12.4。然后它结束于 12.4 + 4.7 = 17.1。因此,对应于 3rd bin 的计数是 tips_df.total_bill
中落入该范围内的值的数量。让我们手动找到它:
>>> tips_df.total_bill.between(12.4, 17.1).sum()
70
(由于我在计算范围时使用了粗略的近似值并省略了精度,所以它并不准确;但我希望你能感觉到。)
到目前为止,这是为了解释为什么直接 value_counts
不直接匹配直方图输出,因为它给出逐值计数,而直方图大约是 范围s.
现在,为什么 seaborn 和 matplotlib 之间的图表不同?这是因为他们使用的垃圾箱数量不同!如果你算一下,matplotlib 有 10 个,seaborn 有 14 个。由于你没有为它们中的任何一个指定 bins
参数,它们使用默认值并且 matplotlib 默认为 plt.rcParams["hist.bins"]
并且 seaborn 选择“自动”(见注释 部分 here).
所以,我们不妨给出 bins
个参数来强制执行相同的输出:
>>> plt.hist(tips_df.total_bill, bins=10)
>>> sns.histplot(tips_df.total_bill, bins=10)
所以我使用的数据集是来自 seaborn 的 tips。
我想针对 total_bill
列绘制直方图,我同时使用了 seaborn 和 matlotlib。
这是我的 matplotlib 直方图:
plt.hist(tips_df.total_bill);
这是我的 seaborn 直方图:
sns.histplot(tips_df.total_bill)
如您所见,在 total_bill
13 附近,频率似乎是最大的。
但是,在 matplotlib 中它大约是 68,而它在 seaborn 中大约是 48。
两者都是错误的。因为打字
tips_df["total_bill"].value_counts().sort_values(ascending=False).head(5)
我们得到输出
13.42 3
15.69 2
10.34 2
10.07 2
20.69 2
Name: total_bill, dtype: int64
我们可以看到,出现次数最多的是13左右,但是为什么y-axis上的计数值不对呢?
在直方图中,“矩形”的高度表示给定 范围 中有多少个值,而这又由矩形的宽度描述。您可以通过 (max - min) / number_of_rectangles.
得到每个矩形的宽度例如,在 matplotlib 的输出中,有 10 个矩形(箱)。由于您的数据最小值约为 3,最大值约为 50,因此每个宽度约为 4.7 个单位宽。现在,为了获得第三个矩形范围,例如,我们从最小值开始并添加此宽度直到我们到达那里,即 3 + 4.7*2 = 12.4。然后它结束于 12.4 + 4.7 = 17.1。因此,对应于 3rd bin 的计数是 tips_df.total_bill
中落入该范围内的值的数量。让我们手动找到它:
>>> tips_df.total_bill.between(12.4, 17.1).sum()
70
(由于我在计算范围时使用了粗略的近似值并省略了精度,所以它并不准确;但我希望你能感觉到。)
到目前为止,这是为了解释为什么直接 value_counts
不直接匹配直方图输出,因为它给出逐值计数,而直方图大约是 范围s.
现在,为什么 seaborn 和 matplotlib 之间的图表不同?这是因为他们使用的垃圾箱数量不同!如果你算一下,matplotlib 有 10 个,seaborn 有 14 个。由于你没有为它们中的任何一个指定 bins
参数,它们使用默认值并且 matplotlib 默认为 plt.rcParams["hist.bins"]
并且 seaborn 选择“自动”(见注释 部分 here).
所以,我们不妨给出 bins
个参数来强制执行相同的输出:
>>> plt.hist(tips_df.total_bill, bins=10)
>>> sns.histplot(tips_df.total_bill, bins=10)