简体   繁体   中英

Adding secondary y-axis with Facetgrid on Seaborn

I have a cohorted dataset (from 1 day to 365 days) that now I am representing like this in Seaborn. The blue line is the previous result, the orange is the current result and the bars are the delta in % between them:

在此处输入图像描述

However, I need to add the bars on the same plot that the lineplot with a secondary axis.

My expected output would be this for each plot of the Facetgrid:

在此处输入图像描述

A sample of the dataframe that I am using on wide format that I splited in two to separate the date from de delta and the pre y post results. I need it this way because of the cohorted data:

在此处输入图像描述

And this is the code I use to plot the first graph:

fig, ax1 = plt.subplots() # initializes figure and plots

ax2 = ax1.twinx() # applies twinx to ax2, which is the second y axis. 

g = sns.FacetGrid(df_ads_long_st, col="m", hue="status", height=5, aspect=0.8)
g.map(sns.lineplot, "dx", "value_a", alpha=.7, ax = ax1)

g = sns.FacetGrid(df_ads_long_de, col="m", hue="status", height=5, aspect=0.8)
g.map(sns.barplot, "dx", "value_a", alpha=.7, ax = ax2)

# these lines add the annotations for the plot. 
ax1.set_xlabel('DX')
ax1.set_ylabel('ARPU', color='b')
ax2.set_ylabel('Delta', color='r')

plt.show(); # shows the plot. 

Is there any other day to do this?

Thanks!

I had a similar requirement. The trick is to create your own function. In this function you create a twin axis.

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


def facetgrid_two_axes(data: pd.DataFrame, x_name: str, y1_name: str, y2_name: str, ylabel1: str, ylabel2: str):
    ax1 = plt.gca()
    sns.lineplot(data[x_name], data[y1_name], alpha=.7, ax=ax1)
    ax1.set_ylabel(ylabel1)

    ax2 = ax1.twinx()
    sns.barplot(data[x_name], data[y2_name], alpha=.7, ax=ax2)
    ax2.set_ylabel(ylabel2)


if __name__ == '__main__':
    df_ads_long_st = pd.DataFrame(...) // Your data

    g = sns.FacetGrid(df_ads_long_st, col="m", hue="status", height=5, aspect=0.8)
    g.map_dataframe(facetgrid_two_axes, x_name="dx", y1_name="value_a", y2_name="value_a", alpha=.7,
                    ylabel1='Counts', ylabel2='Detection rates')

    g.set_xlabels('x data')

    plt.show()

A shortcoming I had, was that the ylabels are shown on every plot instead of only at the borders of the figure.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM