Reputation: 33
I need to show a percentage for my bar graph. However I am not sure how to do it.
sns.set_style('whitegrid')
sns.countplot(y='type',data=df,palette='colorblind')
plt.xlabel('Count')
plt.ylabel('Type')
plt.title('Movie Type in Disney+')
plt.show()
Upvotes: 1
Views: 3659
Reputation: 62513
matplotlib v.3.4.0
, the correct way to annotate bars is with the .bar_label
method, as thoroughly described in How to add value labels on a bar chartseaborn.countplot
returns ax : matplotlib.Axes
, so it's customary to us ax
as the alias for this axes-level method.
Axes
is the explicit interface.python 3.12
, pandas 2.2.2
, matplotlib 3.9.2
, seaborn 0.13.2
ax = sns.countplot(y='type', data=df, palette='colorblind', hue='type', legend=False)
# get the total count of the type column
total = df['type'].count()
# annotate the bars with fmt from matplotlib v3.7.0
for c in ax.containers:
ax.bar_label(c, fmt=lambda x: f'{(x/total)*100:0.1f}%')
# add space at the end of the bar for the labels
ax.margins(x=0.1)
ax.set(xlabel='Count', ylabel='Type', title='Movie Type in Disney+')
plt.show()
ax = sns.countplot(x='type', data=df, palette='colorblind', hue='type', legend=False)
# get the total count of the type column
total = df['type'].count()
# annotate the bars with fmt from matplotlib v3.7.0
for c in ax.containers:
ax.bar_label(c, fmt=lambda x: f'{(x/total)*100:0.1f}%')
plt.show()
v3.4.0 <= matplotlib < v3.7.0
use the labels
parameter.for c in ax.containers:
# for horizontal bars
labels = [f'{(w/total)*100:0.1f}%' if (w := v.get_width()) > 0 else '' for v in c]
# for vertical bars
# labels = [f'{(h/total)*100:0.1f}%' if (h := v.get_height()) > 0 else '' for v in c]
ax.bar_label(c, labels=labels)
Upvotes: 6
Reputation: 1
**For Horizontal:**
plt.rcParams['figure.figsize'] = [8, 8]
ax = sns.countplot(y='Compare Result', data=df, hue='Compare Result',
palette='colorblind', order=df['Compare Result'].value_counts().index)
# get the total count of the type column
total = df['Compare Result'].count()
# count the number of group
group_counts = len(df.groupby('Compare Result').size())
# annotate the bars with fmt from matplotlib v3.7.0
for n in range(group_counts):
ax.bar_label(ax.containers[n], fmt=lambda x: f'{(x/total)*100:0.3f}%')
# add space at the end of the bar for the labels
ax.margins(x=0.1)
ax.set(xlabel='Result Count', ylabel='Compare Result')
plt.show()
**For Vertical:**
plt.rcParams['figure.figsize'] = [6, 6]
# get the total count of the type column
total = df['Compare Result'].count()
ax = sns.countplot(x='Compare Result', data=df, hue='Compare Result',
palette='colorblind', order=df['Compare Result'].value_counts().index)
# add space at the end of the bar for the labels
ax.margins(y=0.1)
# count the number of group
group_counts = len(df.groupby('Compare Result').size())
# annotate the bars with fmt from matplotlib v3.7.0
for n in range(group_counts):
ax.bar_label(ax.containers[n], fmt=lambda x: f'{(x/total)*100:0.3f}%')
ax.set(ylabel='Result Count', xlabel='Compare Result')
plt.show()
Upvotes: 0
Reputation: 96
The beginning code looks great! You just have to calculate the percentage values for each bar by dividing the width of the bar by the total count and multiplying by 100. Then use the annotate function to add those values you calculated as text to the bar. Try the code below and see if it works out for you!
import seaborn as sns
import matplotlib.pyplot as plt
sns.set_style('whitegrid')
# Create the countplot and naming it 'plot'.
plot = sns.countplot(y='type', data=df, palette='colorblind')
plt.xlabel('Count')
plt.ylabel('Type')
plt.title('Movie Type in Disney+')
total = len(df['type'])
for p in plot.patches:
percentage = '{:.1f}%'.format(100 * p.get_width() / total)
x = p.get_x() + p.get_width() + 0.02
y = p.get_y() + p.get_height() / 2
plot.annotate(percentage, (x, y))
plt.show()
Upvotes: 3