英文:
How can I display custom values over grouped bars?
问题
这是你要翻译的内容:
I have a barplot with this values in a `dict` for the C/C):
{'Country Name': {0: 'United States',
  1: 'United States',
  2: 'United States',
  3: 'United States',
  4: 'Russian Federation',
  5: 'Russian Federation',
  6: 'Russian Federation',
  7: 'Russian Federation',
  8: 'Japan',
  9: 'Japan',
  10: 'Japan',
  11: 'Japan',
  12: 'Germany',
  13: 'Germany',
  14: 'Germany',
  15: 'Germany',
  16: 'France',
  17: 'France',
  18: 'France',
  19: 'France'},
 'Indicator Name': {0: 'Population, total',
  1: 'Population, ages 0-14, total',
  2: 'Population, ages 15-64, total',
  3: 'Population, ages 65+, total',
  4: 'Population, total',
  5: 'Population, ages 0-14, total',
  6: 'Population, ages 15-64, total',
  7: 'Population, ages 65+, total',
  8: 'Population, total',
  9: 'Population, ages 0-14, total',
  10: 'Population, ages 15-64, total',
  11: 'Population, ages 65+, total',
  12: 'Population, total',
  13: 'Population, ages 0-14, total',
  14: 'Population, ages 15-64, total',
  15: 'Population, ages 65+, total',
  16: 'Population, total',
  17: 'Population, ages 0-14, total',
  18: 'Population, ages 15-64, total',
  19: 'Population, ages 65+, total'},
 'Valeur': {0: 320896618.0,
  1: 61653419.0,
  2: 212262832.0,
  3: 46980367.0,
  4: 144096870.0,
  5: 24255306.0,
  6: 100404879.0,
  7: 19436685.0,
  8: 127141000.0,
  9: 16517168.0,
  10: 77547638.0,
  11: 33076194.0,
  12: 81686611.0,
  13: 10716271.0,
  14: 53720119.0,
  15: 17250221.0,
  16: 66624068.0,
  17: 12168975.0,
  18: 41837530.0,
  19: 12617563.0}}
Code for the barplot  (with the ax because I tried containers):
ax = plt.figure(figsize=(10,5))
ax = sns.barplot(data = Graph1values, x = 'Country Name', y = 'Valeur', hue = 'Indicator Name',palette="dark")
ax = plt.xlabel('')
ax = plt.ylabel('Nombre de personnes', size = 15)
ax = plt.title('Etude de la répartition de la population', size = 20)
ax = plt.show()
[![enter image description here][1]][1]
I want to add these values on top of the bars
x = ['100%', '19%', '66%', '15%', '100%', '17%', '70%', '13%', '100%', '13%', '61%', '26%', '100%',
 '13%', '66%', '21%', '100%', '18%', '63%', '19%']
I tried with containers, but it does not work.
只提供翻译,不包括问题的回答:
我有一个条形图,其中包含一个`dict`中的这些值,用于C/C):
{'Country Name': {0: '美国',
  1: '美国',
  2: '美国',
  3: '美国',
  4: '俄罗斯联邦',
  5: '俄罗斯联邦',
  6: '俄罗斯联邦',
  7: '俄罗斯联邦',
  8: '日本',
  9: '日本',
  10: '日本',
  11: '日本',
  12: '德国',
  13: '德国',
  14: '德国',
  15: '德国',
  16: '法国',
  
<details>
<summary>英文:</summary>
I have a barplot with this values in a `dict` for the C/C):
    {'Country Name': {0: 'United States',
      1: 'United States',
      2: 'United States',
      3: 'United States',
      4: 'Russian Federation',
      5: 'Russian Federation',
      6: 'Russian Federation',
      7: 'Russian Federation',
      8: 'Japan',
      9: 'Japan',
      10: 'Japan',
      11: 'Japan',
      12: 'Germany',
      13: 'Germany',
      14: 'Germany',
      15: 'Germany',
      16: 'France',
      17: 'France',
      18: 'France',
      19: 'France'},
     'Indicator Name': {0: 'Population, total',
      1: 'Population, ages 0-14, total',
      2: 'Population, ages 15-64, total',
      3: 'Population, ages 65+, total',
      4: 'Population, total',
      5: 'Population, ages 0-14, total',
      6: 'Population, ages 15-64, total',
      7: 'Population, ages 65+, total',
      8: 'Population, total',
      9: 'Population, ages 0-14, total',
      10: 'Population, ages 15-64, total',
      11: 'Population, ages 65+, total',
      12: 'Population, total',
      13: 'Population, ages 0-14, total',
      14: 'Population, ages 15-64, total',
      15: 'Population, ages 65+, total',
      16: 'Population, total',
      17: 'Population, ages 0-14, total',
      18: 'Population, ages 15-64, total',
      19: 'Population, ages 65+, total'},
     'Valeur': {0: 320896618.0,
      1: 61653419.0,
      2: 212262832.0,
      3: 46980367.0,
      4: 144096870.0,
      5: 24255306.0,
      6: 100404879.0,
      7: 19436685.0,
      8: 127141000.0,
      9: 16517168.0,
      10: 77547638.0,
      11: 33076194.0,
      12: 81686611.0,
      13: 10716271.0,
      14: 53720119.0,
      15: 17250221.0,
      16: 66624068.0,
      17: 12168975.0,
      18: 41837530.0,
      19: 12617563.0}}
Code for the barplot  (with the ax because I tried containers):
    ax = plt.figure(figsize=(10,5))
    ax = sns.barplot(data = Graph1values, x = 'Country Name', y = 'Valeur', hue = 'Indicator Name',palette="dark")
    ax = plt.xlabel('')
    ax = plt.ylabel('Nombre de personnes', size = 15)
    ax = plt.title('Etude de la répartition de la population', size = 20)
        
    ax = plt.show()
[![enter image description here][1]][1]
**I want to add these values on top of the bars**
    x = ['100%', '19%', '66%', '15%', '100%', '17%', '70%', '13%', '100%', '13%', '61%', '26%', '100%',
     '13%', '66%', '21%', '100%', '18%', '63%', '19%']
I tried with containers, but it does not work.
  [1]: https://i.stack.imgur.com/mjYqF.png
</details>
# 答案1
**得分**: 1
以下是翻译的内容:
- 似乎`dict`必须是DataFrame的输出,但这不在问题中显示。
- 使用[`.bar_label`][1]来在每个条形图的顶部添加自定义标签。[如何在条形图上添加值标签][2]中有该方法的详细解释。
  - 使用条形图的高度(`h`),`country`和容器`label`,以及DataFrame上的[布尔索引][3],以获取正确的`'percents'`来注释条形图。
  - [此问题][4]的答案没有展示如何获取条形图的自定义值。
- 不要将所有行分配给`ax`,因为它们不返回`matplotlib.axes`。这会覆盖`ax`,因此`ax.bar_label`不起作用。
  - `plt.xlabel`,`plt.ylabel`和`plt.title`返回`matplotlib.text.Text`。
  - 使用`ax = plt.show()`,`type(ax) → NoneType`,因为`plt.show`不返回任何内容。
- **在`python 3.11`,`pandas 1.5.3`,`matplotlib 3.7.1`,`seaborn 0.12.2`中进行了测试**
[![在此输入图片描述][5]][5]
## `df`
```python
          Country Name                 Indicator Name       Valeur percents
0        United States              Population, total  320896618.0     100%
1        United States   Population, ages 0-14, total   61653419.0      19%
2        United States  Population, ages 15-64, total  212262832.0      66%
3        United States    Population, ages 65+, total   46980367.0      15%
4   Russian Federation              Population, total  144096870.0     100%
5   Russian Federation   Population, ages 0-14, total   24255306.0      17%
6   Russian Federation  Population, ages 15-64, total  100404879.0      70%
7   Russian Federation    Population, ages 65+, total   19436685.0      13%
8                Japan              Population, total  127141000.0     100%
9                Japan   Population, ages 0-14, total   16517168.0      13%
10               Japan  Population, ages 15-64, total   77547638.0      61%
11               Japan    Population, ages 65+, total   33076194.0      26%
12             Germany              Population, total   81686611.0     100%
13             Germany   Population, ages 0-14, total   10716271.0      13%
14             Germany  Population, ages 15-64, total   53720119.0      66%
15             Germany    Population, ages 65+, total   17250221.0      21%
16              France              Population, total   66624068.0     100%
17              France   Population, ages 0-14, total   12168975.0      18%
18              France  Population, ages 15-64, total   41837530.0      63%
19              France    Population, ages 65+, total   12617563.0      19%
英文:
- It seems the 
dictmust be the output of a DataFrame, which isn't shown in the OP. - Use 
.bar_labelto add custom labels to the top of each bar. How to add value labels on a bar chart has a thorough explanation of the method.- Use the bar height (
h),country, and containerlabel, with Boolean indexing ondf, to get the correct'percents'to annotate the bars. - The answers to this question do not demonstrate how to get the custom values for the bars.
 
 - Use the bar height (
 - Do not assign all lines to 
ax, as they do not return amatplotlib.axes. This overwritesax, soax.bar_labelwon't work.plt.xlabel,plt.ylabel, andplt.titlereturnmatplotlib.text.Text.- With 
ax = plt.show(),type(ax) → NoneTypebecauseplt.showdoesn't return anything. 
 - Tested in 
python 3.11,pandas 1.5.3,matplotlib 3.7.1,seaborn 0.12.2 
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
# create the dataframe
data = {'Country Name': {0: 'United States', 1: 'United States', 2: 'United States', 3: 'United States', 4: 'Russian Federation', 5: 'Russian Federation', 6: 'Russian Federation', 7: 'Russian Federation', 8: 'Japan', 9: 'Japan', 10: 'Japan', 11: 'Japan', 12: 'Germany', 13: 'Germany', 14: 'Germany', 15: 'Germany', 16: 'France', 17: 'France', 18: 'France', 19: 'France'},
        'Indicator Name': {0: 'Population, total', 1: 'Population, ages 0-14, total', 2: 'Population, ages 15-64, total', 3: 'Population, ages 65+, total', 4: 'Population, total', 5: 'Population, ages 0-14, total', 6: 'Population, ages 15-64, total', 7: 'Population, ages 65+, total', 8: 'Population, total', 9: 'Population, ages 0-14, total', 10: 'Population, ages 15-64, total', 11: 'Population, ages 65+, total', 12: 'Population, total', 13: 'Population, ages 0-14, total', 14: 'Population, ages 15-64, total', 15: 'Population, ages 65+, total', 16: 'Population, total', 17: 'Population, ages 0-14, total', 18: 'Population, ages 15-64, total', 19: 'Population, ages 65+, total'},
        'Valeur': {0: 320896618.0, 1: 61653419.0, 2: 212262832.0, 3: 46980367.0, 4: 144096870.0, 5: 24255306.0, 6: 100404879.0, 7: 19436685.0, 8: 127141000.0, 9: 16517168.0, 10: 77547638.0, 11: 33076194.0, 12: 81686611.0, 13: 10716271.0, 14: 53720119.0, 15: 17250221.0, 16: 66624068.0, 17: 12168975.0, 18: 41837530.0, 19: 12617563.0}}
df = pd.DataFrame(data)
# add the list of percent values to the dataframe, which assumes they're in the correct order (as they appear to be)
df['percents'] = ['100%', '19%', '66%', '15%', '100%', '17%', '70%', '13%', '100%', '13%', '61%', '26%', '100%', '13%', '66%', '21%', '100%', '18%', '63%', '19%']
# create the plot
fig, ax = plt.subplots(figsize=(10, 5))
sns.barplot(data=df, x='Country Name', y='Valeur', hue='Indicator Name', palette="dark", ax=ax)
# customize the plot labels and title
plt.xlabel('')
plt.ylabel('Nombre de personnes', size=15)
plt.title('Etude de la répartition de la population', size=20)
# list of countries for selecting data from df
countries = [v.get_text() for v in ax.get_xticklabels()]  # countries = df['Country Name'].unique() also works
# iterate through the axes bar containers
for c in ax.containers:
    
    # get the label of the current containers
    label = c.get_label()
    # use the height of the bar, country, and label name to get the corresponding percent for the container
    labels = [df.loc[df['Indicator Name'].eq(label) &
                     df['Country Name'].eq(country) &
                     df['Valeur'].eq(h) , 'percents'].iloc[0] if (h := v.get_height()) else '' for (v, country) in zip(c, countries)]
    
    # add the bar label with the custom labels
    ax.bar_label(c, labels=labels)
df
          Country Name                 Indicator Name       Valeur percents
0        United States              Population, total  320896618.0     100%
1        United States   Population, ages 0-14, total   61653419.0      19%
2        United States  Population, ages 15-64, total  212262832.0      66%
3        United States    Population, ages 65+, total   46980367.0      15%
4   Russian Federation              Population, total  144096870.0     100%
5   Russian Federation   Population, ages 0-14, total   24255306.0      17%
6   Russian Federation  Population, ages 15-64, total  100404879.0      70%
7   Russian Federation    Population, ages 65+, total   19436685.0      13%
8                Japan              Population, total  127141000.0     100%
9                Japan   Population, ages 0-14, total   16517168.0      13%
10               Japan  Population, ages 15-64, total   77547638.0      61%
11               Japan    Population, ages 65+, total   33076194.0      26%
12             Germany              Population, total   81686611.0     100%
13             Germany   Population, ages 0-14, total   10716271.0      13%
14             Germany  Population, ages 15-64, total   53720119.0      66%
15             Germany    Population, ages 65+, total   17250221.0      21%
16              France              Population, total   66624068.0     100%
17              France   Population, ages 0-14, total   12168975.0      18%
18              France  Population, ages 15-64, total   41837530.0      63%
19              France    Population, ages 65+, total   12617563.0      19%
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。



评论