【问题标题】:Adding Percentages to sns.countplot - how do I show percentages for two values within the categories?向 sns.countplot 添加百分比 - 如何显示类别中两个值的百分比?
【发布时间】:2020-12-15 14:00:40
【问题描述】:

您好,我正在尝试将百分比添加到我的 countplot 中,其中包含 5 个类别和 2 个值(年龄较大和较年轻)。我试过从 How to add percentages on top of bars in seaborn?

我的代码:

plt.figure(figsize =(7,5))
ax = sb.countplot(data = df_x_1, x = 'concern_virus', hue = 'age')
plt.xticks(size =12)
plt.xlabel('Level of Concern', size = 14)
plt.yticks(size = 12)
plt.ylabel('Number of People', size = 12)
plt.title("Older and Younger People's Concern over the Virus", size = 16)
ax.set_xticklabels(ax.get_xticklabels(), rotation=40, ha="right");

for p in ax.patches:
    percentage = '{:.1f}%'.format(100 * p.get_height()/total)
    x = p.get_x() + p.get_width()
    y = p.get_height()
    ax.annotate(percentage, (x, y),ha='center')
plt.show()

如您所见,百分比没有意义。

【问题讨论】:

    标签: python seaborn


    【解决方案1】:

    问题似乎与上述代码中未定义的变量有关:totaltotal 应该是您要调用 100% 的号码,例如数据框中的总行数。这样所有显示的百分比总和为 100。

    这里是一些示例代码:

    import matplotlib.pyplot as plt
    import pandas as pd
    import numpy as np
    import seaborn as sns
    
    N = 250
    df_x_1 = pd.DataFrame({'concern_virus': np.random.choice(['a', 'b', 'c', 'd', 'e'], N),
                           'age': np.random.choice(['younger', 'older'], N)})
    plt.figure(figsize=(7, 5))
    ax = sns.countplot(data=df_x_1, x='concern_virus', order=['a', 'b', 'c', 'd', 'e'],
                       hue='age', hue_order=['younger', 'older'],
                       palette=['chartreuse', 'darkviolet'])
    plt.xticks(size=12)
    plt.xlabel('Level of Concern', size=14)
    plt.yticks(size=12)
    plt.ylabel('Number of People', size=12)
    plt.title("Older and Younger People's Concern over the Virus", size=16)
    ax.set_xticklabels(ax.get_xticklabels(), rotation=40, ha="right")
    
    total = len(df_x_1)
    for p in ax.patches:
        percentage = f'{100 * p.get_height() / total:.1f}%\n'
        x = p.get_x() + p.get_width() / 2
        y = p.get_height()
        ax.annotate(percentage, (x, y), ha='center', va='center')
    plt.tight_layout()
    plt.show()
    

    要将文本置于栏的中心,选择ha='center' 并将宽度的一半添加到 x 位置会有所帮助。在文本中添加换行符有助于将文本很好地定位在栏的顶部。 plt.tight_layout() 可以帮助将所有标签拟合到情节中。

    Seaborn 可让您通过 order=... 固定 x 轴的顺序。图例元素的顺序和对应的颜色可以通过hue_order=...palette=...设置。

    PS:对于新问题,每个年龄组的总数,而不是直接循环遍历所有条,第一个循环可以访问组:

    import matplotlib.pyplot as plt
    import pandas as pd
    import numpy as np
    import seaborn as sns
    
    label_younger = 'younger'
    label_older = 'older'
    df_younger = pd.DataFrame({'concern_virus': np.random.choice(['a', 'b', 'c', 'd', 'e'], 230)})
    df_older = pd.DataFrame({'concern_virus': np.random.choice(['a', 'b', 'c', 'd', 'e'], 120)})
    df_younger['age'] = label_younger
    df_older['age'] = label_older
    df_x_1 = pd.concat([df_younger, df_older], ignore_index=True)
    
    plt.figure(figsize=(7, 5))
    ax = sns.countplot(data=df_x_1, x='concern_virus', order=['a', 'b', 'c', 'd', 'e'],
                       hue='age', hue_order=[label_younger, label_older],
                       palette=['orangered', 'skyblue'])
    plt.xticks(size=12)
    plt.xlabel('Level of Concern', size=14)
    plt.yticks(size=12)
    plt.ylabel('Number of People', size=12)
    plt.title("Older and Younger People's Concern over the Virus", size=16)
    ax.set_xticklabels(ax.get_xticklabels(), rotation=40, ha="right")
    
    for bars in ax.containers:
        if bars.get_label() == label_younger:
            group_total = len(df_younger)
        else:
            group_total = len(df_older)
        for p in bars.patches:
            # print(p.get_facecolor(), p.get_label())
            percentage = f'{100 * p.get_height() / group_total:.1f}%\n'
            x = p.get_x() + p.get_width() / 2
            y = p.get_height()
            ax.annotate(percentage, (x, y), ha='center', va='center')
    plt.tight_layout()
    plt.show()
    

    【讨论】:

      猜你喜欢
      • 2021-04-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多