Home > Software engineering >  sns.histplot legend colors not matching the output
sns.histplot legend colors not matching the output

Time:04-26

I am creating a combo boxplot\histplot.

Everything runs and I get the output I am expecting except for one thing: The line colors in the legend do not match the output.

Code:

def boxhist(dfx, x):
    variable = dfx[x].values
    np.array(variable).mean()
    np.median(variable)

    f, (ax_box, ax_hist) = plt.subplots(2, sharex=True, gridspec_kw={"height_ratios": (0.5, 2)})
    mean = np.array(variable).mean()
    median = np.median(variable)

    sns.boxplot(variable, ax=ax_box)
    ax_box.axvline(mean, color='orange', linestyle='--')
    ax_box.axvline(median, color='black', linestyle='-')

    sns.histplot(data=variable, ax=ax_hist, kde=True, binwidth=2, facecolor='green').lines[0].set_color('red')
    ax_hist.axvline(mean, color='orange', linestyle='--')
    ax_hist.axvline(median, color='black', linestyle='-')

    plt.title(x, fontsize=10, loc='right')
    plt.legend({'Mean': mean, 'Median': median})
    ax_box.set(xlabel='')
    plt.tight_layout()
    plt.show()

Output:

enter image description here

The mean should be orange. The median should be black.

  1. Why is the legend showing the mean as red and the median as orange?
  2. I want the legend colors to match the plot output. mean\orange, median\black.

CodePudding user response:

You need to add a label in ax_hist.axvline(mean, ...., label='Mean') (and similar for the median). Then matplotlib should automatically add them to the legend (when called without parameters).

Here is some example code:

import matplotlib.pyplot as plt
import seaborn as sns
import pandas as pd
import numpy as np

def boxhist(dfx, x):
     variable = dfx[x].values
     variable.mean()
     np.median(variable)

     f, (ax_box, ax_hist) = plt.subplots(2, sharex=True, gridspec_kw={"height_ratios": (0.5, 2)})
     mean = variable.mean()
     median = np.median(variable)

     sns.boxplot(x=variable, ax=ax_box)
     ax_box.axvline(mean, color='orange', linestyle='--')
     ax_box.axvline(median, color='black', linestyle='-')

     sns.histplot(x=variable, ax=ax_hist, kde=True, binwidth=2, facecolor='green')
     ax_hist.lines[0].set_color('red')

     ax_hist.axvline(mean, color='orange', linestyle='--', label='Mean')
     ax_hist.axvline(median, color='black', linestyle='-', label='Median')

     ax_hist.set_title(x, fontsize=10, loc='right')
     ax_hist.legend()
     # ax_box.set(xlabel='') # has no effect on shared x-axis
     plt.tight_layout()
     plt.show()

dfx = pd.DataFrame({'bmi': np.random.normal(30.2, 5, 100)})
boxhist(dfx, 'bmi')

sns.histplot with mean line

  • Related