Seaborn的boxplot + swarmplot:x代表不同的颜色,hues代表不同的符号 [英] Seaborn's boxplot+swarmplot: different color for x, different symbol for hues

查看:162
本文介绍了Seaborn的boxplot + swarmplot:x代表不同的颜色,hues代表不同的符号的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试使用带有不同的 x 组和其他 hues 的seaborn生成箱线图.看到以下代码:

  tips = sns.load_dataset("tips")sns.stripplot(x ="day",y ="total_bill",hue ="smoker",数据=提示,抖动=真实,Palette ="Set2",split = True,linewidth = 1,edgecolor ='gray')sns.boxplot(x ="day",y ="total_bill",hue ="smoker",data = tips,palette ="Set2",fliersize = 0) 

我想让每个 x 箱形图(在此示例中,每天)使用不同的颜色,而每个 hue (在这种情况下,为烟民/不吸烟者)在战场上用不同的符号表示.

我尝试使用 palette 参数,但没有得到我想要的.我也尝试直接与 artist 玩,但是由于某种原因,更改箱形图的 facecolor 也会更改 edgecolor ,但我不这样做仍然不知道如何更改模拟图上的符号.

解决方案

我意识到,

I'm trying to generate a boxplot using seaborn with a different x groups, and additional hues. See this code:

tips = sns.load_dataset("tips")

sns.stripplot(x="day", y="total_bill", hue="smoker",
              data=tips, jitter=True,
              palette="Set2", split=True,linewidth=1,edgecolor='gray')

sns.boxplot(x="day", y="total_bill", hue="smoker",
            data=tips,palette="Set2",fliersize=0)

I would like to have each x boxplots (in this example, each day) be a different color, while each hue (in this case, smoker/non-smoker) to be represented with a different symbol on the swarmplot.

I've tried to play with the palette argument, but did not get what I wanted. I also tried to play with the artists directly, but changing the facecolor of the boxplot also changes the edgecolor for some reason, and I don't know how to change the symbols on the swarmplot anyway.

解决方案

I realized, when answering this question, that I never proposed my own solution to this question, even though I had hacked something together a while ago.

# From itertools' receipes https://docs.python.org/3/library/itertools.html#itertools-recipes
from itertools import zip_longest
def grouper(iterable, n, fillvalue=None):
    "Collect data into fixed-length chunks or blocks"
    # grouper('ABCDEFG', 3, 'x') --> ABC DEF Gxx"
    args = [iter(iterable)] * n
    return zip_longest(*args, fillvalue=fillvalue)


fig, ax = plt.subplots()
# dummy plots, just to get the Path objects
a = ax.scatter([1,2],[3,4], marker='s')
b = ax.scatter([1,2],[3,4], marker='^')
square_mk, = a.get_paths()
triangle_up_mk, = b.get_paths()
a.remove()
b.remove()

sns.swarmplot(x="day", y="total_bill", hue="smoker", data=tips, dodge=True, size=6, lw=2, edgecolor='k')
swarm_cols = ax.collections

sns.boxplot(x="day", y="total_bill", hue="smoker", data=tips, fliersize=0)
box_cols = ax.artists

ax.legend_.remove()

N_cats = len(np.unique(tips.day))
N_hues = len(np.unique(tips.smoker))
print(N_cats,N_hues)

pastels = matplotlib.cm.get_cmap('Pastel1')
cat_colors =  [pastels(x) for x in np.linspace(0,1,N_cats)]
hue_markers = [square_mk, triangle_up_mk]

for boxes,color in zip(grouper(box_cols, N_hues),cat_colors):
    for box in boxes:
        box.set_facecolor(color)
for swarms,color in zip(grouper(swarm_cols, N_hues), cat_colors):
    for swarm,marker in zip(swarms,hue_markers):
        print(swarm, len(swarm.get_offsets()))
        swarm.set_paths([marker])
        swarm.set_facecolors([color])
        swarm.set_linewidths([1.])
        swarm.set_edgecolors(['xkcd:dark grey'])

# recreate legend
for swarm,marker in zip(swarm_cols[-2:],hue_markers):
    print(swarm, len(swarm.get_offsets()))
    swarm.set_paths([marker])
    swarm.set_facecolors(["none"])
    swarm.set_linewidths([1.])
    swarm.set_edgecolors(['xkcd:dark grey'])
ax.legend(swarm_cols[-2:],np.unique(tips.smoker))

这篇关于Seaborn的boxplot + swarmplot:x代表不同的颜色,hues代表不同的符号的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆