【问题标题】:How to add legend on Seaborn facetgrid bar plot如何在 Seaborn facetgrid 条形图上添加图例
【发布时间】:2015-11-22 13:24:25
【问题描述】:

我有以下代码:

import numpy as np
import pandas as pd
import matplotlib
matplotlib.use('Agg')
import matplotlib.pyplot as plt
matplotlib.style.use('ggplot')
import seaborn as sns

sns.set(style="white")

# Create a dataset with many short random walks
rs = np.random.RandomState(4)
pos = rs.randint(-1, 2, (10, 5)).cumsum(axis=1)
pos -= pos[:, 0, np.newaxis]
step = np.tile(range(5), 10)
walk = np.repeat(range(10), 5)
df = pd.DataFrame(np.c_[pos.flat, step, walk],
                  columns=["position", "step", "walk"])



# Initialize a grid of plots with an Axes for each walk
grid = sns.FacetGrid(df, col="walk", hue="walk", col_wrap=5, size=5,
        aspect=1)


# Draw a bar plot to show the trajectory of each random walk
grid.map(sns.barplot, "step", "position", palette="Set3").add_legend();

grid.savefig("/Users/mymacmini/Desktop/test_fig.png")
#sns.plt.show()

这使得这个情节:

如您所见,我把图例弄错了。我怎样才能使它正确?

【问题讨论】:

  • 你应该使用factorplot,或者如果你真的想直接使用FacteGrid,你必须在map中传递hue变量。
  • @mwaskom 非常感谢。你能举个例子吗?我试过这个但也失败了grid.map(sns.barplot, "step", "position", hue="step", palette="Set3").add_legend();
  • 这是第三个位置参数。但是你真的应该使用factorplot...
  • @mwaskom 对不起。我的意思是我尝试了这个grid = sns.factorplot(x="step",y="position", col="walk", kind="bar", data=df, col_wrap=4, aspect=1, size=5, palette="Set3").add_legend(),但没有出现图例。

标签: python pandas matplotlib seaborn


【解决方案1】:

每个子图都有一个图例项。看起来如果我们想让图例与每个子图中的条相对应,我们必须手动制作它们。

# Let's just make a 1-by-2 plot
df = df.head(10)

# Initialize a grid of plots with an Axes for each walk
grid = sns.FacetGrid(df, col="walk", hue="walk", col_wrap=2, size=5,
        aspect=1)

# Draw a bar plot to show the trajectory of each random walk
bp = grid.map(sns.barplot, "step", "position", palette="Set3")

# The color cycles are going to all the same, doesn't matter which axes we use
Ax = bp.axes[0]

# Some how for a plot of 5 bars, there are 6 patches, what is the 6th one?
Boxes = [item for item in Ax.get_children()
         if isinstance(item, matplotlib.patches.Rectangle)][:-1]

# There is no labels, need to define the labels
legend_labels  = ['a', 'b', 'c', 'd', 'e']

# Create the legend patches
legend_patches = [matplotlib.patches.Patch(color=C, label=L) for
                  C, L in zip([item.get_facecolor() for item in Boxes],
                              legend_labels)]

# Plot the legend
plt.legend(handles=legend_patches)

【讨论】:

  • a, b, c, d, e 来自哪里?这与数据集中的任何内容都不对应。
  • 我只是编的。它不在虚拟数据集中(或者它只是[0, 1, 2, 3, 4],x 值)。我有点猜测真实数据集,OP 可能有与每个类相关的有意义的标签。
  • 我认为 OP 希望图例标签成为数据框 step 列中的唯一值
【解决方案2】:

当传说不成功时,您总是可以像这样轻松地制作自己的:

import matplotlib

name_to_color = {
    'Expected':   'green',
    'Provided':   'red',
    'Difference': 'blue',
}

patches = [matplotlib.patches.Patch(color=v, label=k) for k,v in name_to_color.items()]
matplotlib.pyplot.legend(handles=patches)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-05-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-09-24
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多