pythonmatplotlibseaborncountplot

Issue in adding percentages to the top of bars in seaborn countplot


In a countplot I need to add percentages on top of the bars. I already tried the solution given in this post. But I am getting the percentage only for the first bar and not for the remaining. Is there any way to get it solved? Code snippet as below:

import pandas as pd
my_data_set = pd.DataFrame({'ydata': ['N', 'N', 'N', 'N', 'N', 'N', 'Y', 'N', 'Y', 'N', 'N'], 
               'p_f_test': ['False', 'True', 'True', 'True', 'False', 'False', 'False', 'False', 'False', 'False', 'True']}) 

total = float(len(my_data_set))
ax = sns.countplot(x='p_f_test',hue='ydata',data=my_data_set)
for p in ax.patches:
    height = p.get_height()
    ax.text(p.get_x()+p.get_width()/2., height + 3, '{:1.2f}'.format(height/total), ha="center").astype(int)

Solution

  • You have a bar in your plot that does not have an extent, i.e. get_height is NaN. You need to explicitely catch that case. Possibly you want to use 0 instead.

    import numpy as np
    import seaborn as sns
    import matplotlib.pyplot as plt
    import pandas as pd
    
    my_data_set = pd.DataFrame({'ydata': ['N', 'N', 'N', 'N', 'N', 'N', 'Y', 'N', 'Y', 'N', 'N'], 
                   'p_f_test': ['False', 'True', 'True', 'True', 'False', 'False', 'False', 'False', 'False', 'False', 'True']}) 
    
    total = float(len(my_data_set))
    ax = sns.countplot(x='p_f_test',hue='ydata',data=my_data_set)
    for p in ax.patches:
        height = p.get_height()
        if np.isnan(height):
            height=0
        ax.text(p.get_x()+p.get_width()/2., height, '{:1.2f}'.format(height/total), ha="center")
    
    plt.show()