简体   繁体   English

在将值标签添加到Pandas数据框条形图时遇到麻烦

[英]Having trouble with adding value labels to a Pandas dataframe bar plot

I've been struggling to add a simple thing as value labels to a Pandas dataframe bar plot. 我一直在努力为Pandas数据框条形图添加一个简单的东西作为值标签。 I've looked at over 20 threads (with these three being the most helpful - How can I display text over columns in a bar chart in matplotlib? , matplotlib advanced bar plot and Python pandas / matplotlib annotating labels above bar chart columns and nothing is working. 我研究了20多个线程(这三个线程最有帮助- 如何在matplotlib的条形图中的列上显示文本?matplotlib高级条形图Python pandas / matplotlib注释条形图列上方的标签 ,什么都没有工作。

My data is not at all complex. 我的数据一点也不复杂。 The dataframe structure is: 数据框结构为:

+------+----------+----------+----------+----------+-------+
| Year | Product1 | Product2 | Product3 | Product4 | Total |
+------+----------+----------+----------+----------+-------+
| 2005 |      123 |      123 |      123 |      123 |   492 |
| 2006 |      111 |      111 |      111 |      111 |   444 |
+------+----------+----------+----------+----------+-------+

with year being the index for the dataframe. 年是数据框的索引。

The representation I'm looking for is simple. 我要寻找的表示很简单。 A stacked bar chart of all the products, with only the value label for 'Total' being displayed at the top of the stacked column (I don't want to represent 'Total' in the chart). 所有产品的堆叠条形图,在堆叠列的顶部仅显示“总计”的值标签(我不想在图表中表示“总计”)。

The code that I've currently is: 我当前的代码是:

fig,ax = plt.subplots()
ax =df.ix[:,df.columns.difference(['Total'])].plot.bar(stacked=True, colormap='coolwarm',figsize=(14,12),ax=ax)
ax.set_ylabel("Total sales", fontsize=14)
ax.set_xlabel("Year", fontsize=14)
ax.legend(loc='best', fancybox=True, framealpha=0.5)
for i, label in enumerate(list(df.index)):
    score = df.ix[label]['Total']
    ax.annotate(str(score), (i - 0.2, score))
fig = ax.get_figure()
fig.savefig('sumplot.png',dpi=100,bbox='Tight')

What I'm getting right now are values that are way off in the sky. 我现在正在得到的是远在天边的价值观。 I think this is because the height is being determined by the 'Total'+the values of all the other columns? 我认为这是因为高度是由“总计” +所有其他列的值确定的? Is there anyway to modify this so that the height is just the height of 'Total'? 无论如何,有没有修改它,使高度仅为“总计”的高度? Fiddling with the value of score in the ax.annotate snippet doesnt help because in there is wide variation in the data values (the data structure above is just representative - not actual data) 在ax.annotate片段中调整score的值无济于事,因为数据值存在很大差异(上面的数据结构仅是代表性的而非实际数据)

I ran the following code, and didn't modify much. 我运行了以下代码,并没有做太多修改。 All I did was set the year as index of the dataframe, and update th .ix to the .loc method call. 我所做的只是将年份设置为数据框的索引,并将.ix更新为.loc方法调用。

Your problem might have been caused by not plotting against the year, but against a numerical index, which would then include the year as a value to be plotted on top of the data you are interested in. 您的问题可能是由于不是根据年份绘制,而是针对数字索引而引起的,数字索引随后会将年份作为要绘制的值包括在您感兴趣的数据之上。

If I understand your question correctly the following code produces your desired results. 如果我正确理解您的问题,则以下代码将产生所需的结果。 I will ad a picture of my plot for you to verify. 我会为我的地块做广告,供您验证。

Plot of data 数据图

import matplotlib.pyplot as plt
import pandas as pd

data = {
    "Year": [2005, 2006],
    "Product1": [123, 111],
    "Product2": [123, 111],
    "Product3": [123, 111],
    "Product4": [123, 111],
    "Total": [492, 444]
}

df = pd.DataFrame(data).set_index("Year", drop=True)

fig,ax = plt.subplots()
ax =df.loc[:,df.columns.difference(['Total'])].plot.bar(stacked=True, colormap='coolwarm',figsize=(14,12),ax=ax)
ax.set_ylabel("Total sales", fontsize=14)
ax.set_xlabel("Year", fontsize=14)
ax.legend(loc='best', fancybox=True, framealpha=0.5)
for i, label in enumerate(list(df.index)):
    score = df.loc[label]['Total']
    ax.annotate(str(score), (i - 0.2, score))
fig = ax.get_figure()
fig.savefig('sumplot.png',dpi=100,bbox='Tight')

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM