I wanted to display only half error bars, as they are symetric ; as I had no clue how to do this with a "clean way", I chose to use asymetric errors with 0 on the bottom side ; but then, when I displayed caps, I realised this was not the best way to do this.
Here's the code :
import numpy as np
import matplotlib.pyplot as plt
N = 5
men_means = (20, 35, 30, 35, 27)
men_std = (2, 3, 4, 1, 2)
ind = np.arange(N)
width = 0.35
fig, ax = plt.subplots()
rects1 = ax.bar(ind, men_means, width, color='r',yerr=[np.zeros(len(men_std)),men_std],capsize = 5)
women_means = (25, 32, 34, 20, 25)
women_std = (3, 5, 2, 3, 3)
rects2 = ax.bar(ind + width, women_means, width, color='y',yerr=[np.zeros(len(women_std)),women_std],capsize = 5)
plt.show()
And this is the plot I get :. As you can see, my way of plotting half error bars is probably not what should be done.
So is there any way to hide the bottom cap line or a better way to plot half error bars ?
ax.errorbar
has the option to set uplims=True
or lolims=True
to signify that the means repesent the upper or lower limits, respectively. Unfortunately, it doesn't seem like you can use these options directly with ax.bar
, so we have to plot the errorbar and the bar plot separately.
The documentation for the uplims/lolims
options in ax.errorbar
:
lolims
/uplims
/xlolims
/xuplims
: bool, optional, default:NoneThese arguments can be used to indicate that a value gives only upper/lower limits. In that case a caret symbol is used to indicate this. lims-arguments may be of the same type as
xerr
andyerr
. To use limits with inverted axes,set_xlim()
orset_ylim()
must be called before errorbar().
Note that using this option changes your caps to arrows. See below for an example of how to change them back to caps, if you need flat caps instead of arrows.
You can see these options in action in this example on the matplotlib website.
Now, here's your example, modified:
import numpy as np
import matplotlib.pyplot as plt
N = 5
men_means = (20, 35, 30, 35, 27)
men_std = (2, 3, 4, 1, 2)
ind = np.arange(N)
width = 0.35
fig, ax = plt.subplots()
rects1 = ax.bar(ind, men_means, width, color='r')
err1 = ax.errorbar(ind, men_means, yerr=men_std, lolims=True, capsize = 0, ls='None', color='k')
women_means = (25, 32, 34, 20, 25)
women_std = (3, 5, 2, 3, 3)
rects2 = ax.bar(ind + width, women_means, width, color='y')
err2 = ax.errorbar(ind + width, women_means, yerr=women_std, lolims=True, capsize = 0, ls='None', color='k')
plt.show()
If you don't like the arrows, you change them to flat caps, by changing the marker of the caplines
that are returned (as the second item) from ax.errorbar
. We can change them from the arrows to the marker style _
, and then control their size with .set_markersize
:
import numpy as np
import matplotlib.pyplot as plt
N = 5
men_means = (20, 35, 30, 35, 27)
men_std = (2, 3, 4, 1, 2)
ind = np.arange(N)
width = 0.35
fig, ax = plt.subplots()
rects1 = ax.bar(ind, men_means, width, color='r')
plotline1, caplines1, barlinecols1 = ax.errorbar(
ind, men_means, yerr=men_std, lolims=True,
capsize = 0, ls='None', color='k')
caplines1[0].set_marker('_')
caplines1[0].set_markersize(20)
women_means = (25, 32, 34, 20, 25)
women_std = (3, 5, 2, 3, 3)
rects2 = ax.bar(ind + width, women_means, width, color='y')
plotline2, caplines2, barlinecols2 = ax.errorbar(
ind + width, women_means, yerr=women_std,
lolims=True, capsize = 0, ls='None', color='k')
caplines2[0].set_marker('_')
caplines2[0].set_markersize(10)
plt.show()
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With