Customize violin plot demo, see #6723#6814
Conversation
|
Yes, please ensure you have run |
|
|
||
|
|
||
| # functions to calculate percentiles and adjacent values | ||
| def percentile(vals, p): |
|
I am 👍 on this example over all, thank you for this! I left some comments on how to make it better, but would not have any problem with this being merged as-is. attn @story645 |
|
|
||
| ax.get_xaxis().set_tick_params(direction='out') | ||
| ax.xaxis.set_ticks_position('bottom') | ||
| ax.set_xticks([x+1 for x in range(len(lab))]) |
|
@tacaswell I am not familiar with python enough though, please modify the example as necessary to adhere to your coding standards. |
|
I kind of would prefer it get simplified as I think some of the boilerplate is making it really hard to follow and sort of distracting from the core of the example. If np.percentile and a call to vlines and the like work equally well, I vote for that. I don't love that that data is random as it makes the example very non-deterministic and really the best structure for the data is a record array/pandas dateframe 'cause of how it's passed into the functions but that's also overkill. Also kinda think the facecolors should vary, mostly to fully show the feature. Eta: @pd3 what's @tacaswell is getting at is that you can use numpy to refactor a lot of your code. Here's a rough pass, but I would still like to simplify more: import matplotlib.pyplot as plt
import numpy as np
def adjacent_values(vals):
q1, q3 = np.percentile(vals, [25, 75])
uav = q3 + (q3-q1)*1.5
uav = np.clip(uav, q3, vals[-1])
lav = q1 - (q3-q1)*1.5
lav = np.clip(lav, vals[0], q1)
return [lav, uav]
# create test data
prng = np.random.RandomState(123456)
data = [sorted(prng.random.normal(0, std, 100)) for std in range(6,10)]
medians = [np.percentile(d, 50) for d in data]
# upper and lower adjacent values
avmin, avmax = list(zip(*[adjacent_values(d) for d in data]))
#inter-quantile ranges
iqrmin, iqrmax = list(zip(*[np.percentile(d, [25, 75]) for d in data]))
# plot the violins
fig, ax = plt.subplots(nrows=1, ncols=1, figsize=(7, 5))
parts = ax.violinplot(data, showextrema=False)
# customize colors
for pc in parts['bodies']:
pc.set_facecolor('#D43F3A')
pc.set_edgecolor('black')
pc.set_alpha(1)
#plot median
inds = np.arange(1, len(medians)+1)
ax.scatter(inds, medians, marker='o', edgecolor='none', color='white', s=50, zorder=3)
ax.vlines(inds, avmin, avmax, color='k', linestyle='-', lw=1)
ax.vlines(inds, iqrmin, iqrmax, color='k', linestyle='-', lw=5)
ax.set_xticks(inds)
ax.set_xticklabels(['a', 'b', 'c', 'd'])
ax.set_xlim(0.25, inds[-1] + 0.75)
ax.set_title('customized violin plot') |
|
@story645 I do understand. Please modify the code as you deem fit, or otherwise ignore the pull request :-) |
|
Well it's your PR...I'm not trying to dictate anything here, just making a suggestion about what I think might be clearer-I could totally be wrong here and feel free to disagree. Honestly, I'm having an internal debate over my own code 'cause of all the |
|
The code is clean, and this is an nice addition to the gallery. I'd merged it as is, and do the modifications asked by @tacaswell and let @story645 improve the code in another PR (or I can put one of my students on it.) |
|
Plan for this:
|
DOC: Customize violin plot demo Add violin plot example with customized colors closes #6723
|
Backported to v2.x fc88474 |
No description provided.