我有一个带有变量“ x”和“标志”的数据框,如下所示:
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
import numpy as np
import random
x_a = [np.random.normal() for y in range(10**4)]
x_b = [np.random.normal() for y in range(10**3)]
#x_c = [np.random.normal() for y in range(10**2)] # in this case density=True works fine
x_c = [random.choice([0, 1, 2]) for y in range(10**2)] # in this case density=True doesn't work
x = x_a + x_b + x_c
flag_a = ['a' for y in range(10**4)]
flag_b = ['b' for y in range(10**3)]
flag_c = ['c' for y in range(10**2)]
flag = flag_a + flag_b + flag_c
df = pd.DataFrame({'x': x, 'flag': flag})
df.head()
x flag
0 1.311679 a
1 -1.096678 a
2 0.118205 a
3 1.364317 a
4 0.542725 a
我想为每个标志获取x的直方图,尝试使用
g = sns.FacetGrid(df, col='flag')
g.map(plt.hist, 'x', bins=20)
导致
我想知道相对频率,以便比较具有不同计数的标志之间的分布。
请注意,density=True
无济于事。
g = sns.FacetGrid(df, col='flag')
g.map(plt.hist, 'x', bins=20, density=True)
给予
当垃圾箱真的很“薄”时,它们会变得很高,并且垂直轴大于1。我不想要它,因为我希望最大值为1 = 100%。
答案 0 :(得分:2)
如果为此需要使用seaborn
,则在创建sharey
(https://www.php.net/manual/en/curlfile.construct.php)时需要将False
设置为FacetGrid
。所以改变
g = sns.FacetGrid(df, col='flag')
到
g = sns.FacetGrid(df, col='flag', sharey=False)
你会得到
对于带有np.random.normal()
或
代表np.random.choice([0, 1, 2])
。应该与density=True
或density=False
一起使用。
替代方法是直接创建轴对象,如果您需要对其对象的创建和缩放进行更精细的控制等...
fig, axs = plt.subplots(ncols=3, figsize=(12, 4))
flags = ['a', 'b', 'c']
for ax, flag in zip(axs, flags):
h = max(np.histogram(df[df['flag'] == flag]['x'].values, bins=20)[0])
ax.hist(df[df['flag'] == flag]['x'].values, bins=20)
ax.set_ylim([0, h*1.1])
plt.show()