我正在尝试使用Pandas DataFrame
中的数据来绘制类似的内容。日期是介于0到100之间的数字,代表百分比。我有3栏代表3个不同的类别,每个类别都有百分比值。
我想要得到什么:
使用此代码后,我会得到什么:
df_margins = pd.read_excel("path to excel file")
df_margins.reset_index(drop=True, inplace=True)
df_margins_sort = pd.DataFrame(np.sort(df_margins.values, axis=0), index=df_margins.index, columns=df_margins.columns)
df_margins_sort.hist( alpha=0.5)
尝试使用seaborn
库,我得到了:
x = df_margins_sort["safety_margin_distribution_0"].tolist()
y = df_margins_sort["safety_margin_distribution_5"].tolist()
z = df_margins_sort["safety_margin_distribution_10"].tolist()
ggg = [x,y,z]
fig, ax = plt.subplots()
for a in ggg:
sns.distplot(a, bins=range(1, 100, 10), ax=ax, kde=False)
ax.set_xlim([0, 100])
79.6657 8.3008 12.0334
28 72 0
51.4077 48.5923 0
84.1176 2.7451 13.1373
79.5455 1.0101 19.4444
51.9205 48.0795 0
57.2877 6.5906 36.1217
71.2589 11.4014 17.3397
56.2624 43.7376 0
76.4228 0 23.5772
51.8473 6.6502 41.5025
74.8555 25.1445 0
85.8254 14.1746 0
63.2754 0.7444 35.9801
答案 0 :(得分:2)
您可以尝试在同一轴上绘制各个历史记录:
np.random.seed(1)
df = pd.DataFrame(np.random.randint(0,10,(100,3)), columns=list('abc'))
fig, ax = plt.subplots()
for col in df.columns:
df[col].hist(alpha=0.3, ax=ax, label=col)
ax.legend()
输出,顺便说一句,它看起来像您的原始输出:
答案 1 :(得分:1)
seaborn
: safety_margin_distribution_5 safety_margin_distribution_10 safety_margin_distribution_0
79.6657 8.3008 12.0334
28.0000 72.0000 0.0000
51.4077 48.5923 0.0000
84.1176 2.7451 13.1373
79.5455 1.0101 19.4444
51.9205 48.0795 0.0000
57.2877 6.5906 36.1217
71.2589 11.4014 17.3397
56.2624 43.7376 0.0000
76.4228 0.0000 23.5772
51.8473 6.6502 41.5025
74.8555 25.1445 0.0000
85.8254 14.1746 0.0000
63.2754 0.7444 35.9801
seaborn.distplot
seaborn
的关键问题是没有提供label
并且没有致电plt.legend()
[x, y, z]
那样为每一列创建单独的对象import seaborn as sns
import pandas as pd
import matplotlib.pyplt as plt
plt.figure(figsize=(7, 6))
for col in df.columns:
sns.distplot(df[col], label=col,
bins=range(0, 101, 10),
kde=False, hist_kws=dict(edgecolor='black'))
plt.xlabel('Value Range')
plt.ylabel('Frequency')
plt.legend()
plt.xticks(range(0, 101, 10))
plt.show()
bins
的{{1}}参数设置垃圾箱的大小,但是要在刻度线上加上标签,请使用distplot
答案 2 :(得分:0)
我想提出一种不同的方法。它不能避免先天不足,但可以避免循环。
工作流程就在其中:读入数据,转换为整齐(长)格式,然后将直方图映射到深海的Facet Grid:
从io导入StringIO 进口大熊猫 进口seaborn
seaborn.set(style ='ticks')
data = StringIO("""\
safety_margin_distribution_5 safety_margin_distribution_10 safety_margin_distribution_0
79.6657 8.3008 12.0334
28.0000 72.0000 0.0000
51.4077 48.5923 0.0000
84.1176 2.7451 13.1373
79.5455 1.0101 19.4444
51.9205 48.0795 0.0000
57.2877 6.5906 36.1217
71.2589 11.4014 17.3397
56.2624 43.7376 0.0000
76.4228 0.0000 23.5772
51.8473 6.6502 41.5025
74.8555 25.1445 0.0000
85.8254 14.1746 0.0000
63.2754 0.7444 35.9801
""")
df = (
pandas.read_csv(data, sep='\s+')
.stack()
.to_frame('Safety Margin')
.reset_index(level=0, drop=True)
.assign(Distribution=lambda df: df.index.str.rsplit('_', 1).map(lambda x: int(x[-1])))
.reset_index(drop=True)
.pipe((seaborn.FacetGrid, 'data'), hue='Distribution', size=5)
.map(seaborn.distplot, 'Safety Margin', kde=False, bins=range(0, 100, 5))
.add_legend()
)
我并不是说这比基于循环的答案更好。但是使用整洁的数据并在构面网格上进行映射可能会有好处(例如,如果您决定将图进一步分为行和列)