简体   繁体   English

Plotly:如何使用 python 创建子图?

[英]Plotly:How to create subplots with python?

I am wondering what is best practice to create subplots using Python Plotly.我想知道使用 Python Plotly 创建子图的最佳实践是什么。 Is it to use plotly.express or the standard plotly.graph_objects ?是使用plotly.express还是standard plotly.graph_objects

I'm trying to create a figure with two subplots, which are stacked bar charts.我正在尝试创建一个带有两个子图的图形,它们是堆积条形图。 The following code doesn't work.以下代码不起作用。 I didn't find anything useful in the official documentation.我在官方文档中没有找到任何有用的东西。 The classic Titanic dataset was imported as train_df here.经典泰坦尼克号数据集在此处作为train_df导入。

import plotly.express as px

train_df['Survived'] = train_df['Survived'].astype('category')
fig1 = px.bar(train_df, x="Pclass", y="Age", color='Survived')
fig2 = px.bar(train_df, x="Sex", y="Age", color='Survived')

trace1 = fig1['data'][0]
trace2 = fig2['data'][0]

fig = make_subplots(rows=1, cols=2, shared_xaxes=False)
fig.add_trace(trace1, row=1, col=1)
fig.add_trace(trace2, row=1, col=2)

fig.show()

I got the following figure:我得到了下图:

在此处输入图片说明

What I expect is as follows:我的期望如下:

在此处输入图片说明

From what I know, it's not possible to subplot stakedbar (because stacked bar are in facted figures and not traces)...据我所知,不可能对 stakedbar 进行子绘图(因为堆叠的条形图实际上是数字而不是痕迹)...

On behalf of fig.show(), you can put to check if the html file is okay for you (The plots are unfortunately one under the other...) :代表 fig.show(),您可以检查 html 文件是否适合您(不幸的是,这些图在另一个下方......):

with open('p_graph.html', 'a') as f:
    f.write(fig1.to_html(full_html=False, include_plotlyjs='cdn',default_height=500))
    f.write(fig2.to_html(full_html=False, include_plotlyjs='cdn',default_height=500))

try the code below to check if the html file generate can be okay for you:试试下面的代码来检查生成的 html 文件是否适合你:

import pandas as pd
import plotly.graph_objects as go

#Remove the .astype('category') to easily 
#train_df['Survived'] = train_df['Survived'].astype('category')
Pclass_pivot=pd.pivot_table(train_df,values='Age',index='Pclass',
                   columns='Survived',aggfunc=lambda x: len(x))
Sex_pivot=pd.pivot_table(train_df,values='Age',index='Sex',
                   columns='Survived',aggfunc=lambda x: len(x))

fig1 = go.Figure(data=[
    go.Bar(name='Survived', x=Pclass_pivot.index.values, y=Pclass_pivot[1]),
    go.Bar(name='NotSurvived', x=Pclass_pivot.index.values, y=Pclass_pivot[0])])

# Change the bar mode
fig1.update_layout(barmode='stack')


fig2 = go.Figure(data=[
    go.Bar(name='Survived', x=Sex_pivot.index.values, y=Sex_pivot[1]),
    go.Bar(name='NotSurvived', x=Sex_pivot.index.values, y=Sex_pivot[0])])
# Change the bar mode
fig2.update_layout(barmode='stack')

with open('p_graph.html', 'a') as f:
    f.write(fig1.to_html(full_html=False, include_plotlyjs='cdn',default_height=500))
    f.write(fig2.to_html(full_html=False, include_plotlyjs='cdn',default_height=500))

I'm hoping that the existing answer suits your needs, but I'd just like to note that the statement我希望现有的答案适合您的需求,但我只想指出该声明

it's not possible to subplot stakedbar (because stacked bar are in facted figures and not traces不可能对 stakedbar 进行子图(因为堆叠的条形图实际上是数字而不是痕迹

is not entirely correct.不完全正确。 It's possible to build a plotly subplot figure using stacked bar charts as long as you put it together correctly using add_trace() and go.Bar() .只要您使用add_trace()go.Bar()将其正确组合在一起,就可以使用堆积条形图构建一个可绘制的子图。 And this also answers your question regarding:这也回答了您关于以下方面的问题:

I am wondering what is best practice to create subplots using Python Plotly.我想知道使用 Python Plotly 创建子图的最佳实践是什么。 Is it to use plotly.express or the standard plotly.graph_objects?是使用 plotly.express 还是标准的 plotly.graph_objects?

Use plotly.express ff you find a px approach that suits your needs.使用plotly.express ff 您会找到适合您需求的px方法。 And like in your case where you do not find it;而像你的情况,你do not找它; build your own subplots using plotly.graphobjects .使用plotly.graphobjects构建您自己的子图。

Below is an example that will show you one such possible approach using the titanic dataset.下面是一个示例,它将向您展示使用titanic数据集的一种可能的方法。 Note that the column names are noe the same as yours since there are no capital letters.请注意,列名与您的不同,因为没有大写字母。 The essence of this approav is that you use go.Bar() for each trace, and specify where to put those traces using the row and col arguments in go.Bar() .这approav的本质是,你使用go.Bar()每道,并指定把使用这些痕迹rowcol论点go.Bar() If you assign multiple traces to the same row and col , you will get stacked bar chart subplots if you specify barmode='stack' in fig.update_layout(). Using如果您将多个跟踪分配给同一rowcol ,如果您在fig.update_layout(). Using指定barmode='stack' ,您将获得堆积的条形图子图fig.update_layout(). Using fig.update_layout(). Using px.colors.qualitative.Plotly[i]` will let you assign colors from the standard plotly color cycle sequentially. fig.update_layout(). Using px.colors.qualitative.Plotly[i]` 可以让您从标准绘图颜色循环中按顺序分配颜色。

Plot:阴谋:

在此处输入图片说明

Code:代码:

from plotly.subplots import make_subplots
import plotly.graph_objects as go
import plotly.express as px
import pandas as pd

url = "https://raw.github.com/mattdelhey/kaggle-titanic/master/Data/train.csv"
titanic = pd.read_csv(url)
#titanic.info()
train_df=titanic
train_df

# data for fig 1
df1=titanic.groupby(['sex', 'pclass'])['survived'].aggregate('mean').unstack()

# plotly setup for fig
fig = make_subplots(2,1)
fig.add_trace(go.Bar(x=df1.columns.astype('category'), y=df1.loc['female'],
                     name='female',
                     marker_color = px.colors.qualitative.Plotly[0]),
    row=1, col=1)


fig.add_trace(go.Bar(x=df1.columns.astype('category'), y=df1.loc['male'],
                     name='male',
                     marker_color = px.colors.qualitative.Plotly[1]),
    row=1, col=1)


# data for plot 2
age = pd.cut(titanic['age'], [0, 18, 80])
df2 = titanic.pivot_table('survived', [age], 'pclass')
groups=['(0, 18]', '(18, 80]']

fig.add_trace(go.Bar(x=df2.columns, y=df2.iloc[0],
                     name=groups[0],
                     marker_color = px.colors.qualitative.Plotly[3]),
    row=2, col=1)

fig.add_trace(go.Bar(x=df2.columns, y=df2.iloc[1],
                     name=groups[1],
                     marker_color = px.colors.qualitative.Plotly[4]),
    row=2, col=1)

fig.update_layout(title=dict(text='Titanic survivors by sex and age group'), barmode='stack', xaxis = dict(tickvals= df1.columns))
fig.show()

fig.show()

I managed to generate the subplots using the add_bar function.我设法使用add_bar函数生成子图。

Code:代码:

from plotly.subplots import make_subplots

# plotly can only support one legend per graph at the moment.
fig = make_subplots(
    rows=1, cols=2,
    subplot_titles=("Pclass vs. Survived", "Sex vs. Survived")
)
fig.add_bar(
    x=train_df[train_df.Survived == 0].Pclass.value_counts().index,
    y=train_df[train_df.Survived == 0].Pclass.value_counts().values,
    text=train_df[train_df.Survived == 0].Pclass.value_counts().values,
    textposition='auto',
    name='Survived = 0',
    row=1, col=1
)
fig.add_bar(
    x=train_df[train_df.Survived == 1].Pclass.value_counts().index,
    y=train_df[train_df.Survived == 1].Pclass.value_counts().values,
    text=train_df[train_df.Survived == 1].Pclass.value_counts().values,
    textposition='auto',
    name='Survived = 1',
    row=1, col=1
)
fig.add_bar(
    x=train_df[train_df.Survived == 0].Sex.value_counts().index,
    y=train_df[train_df.Survived == 0].Sex.value_counts().values,
    text=train_df[train_df.Survived == 0].Sex.value_counts().values,
    textposition='auto',
    marker_color='#636EFA',
    showlegend=False,
    row=1, col=2
)
fig.add_bar(
    x=train_df[train_df.Survived == 1].Sex.value_counts().index,
    y=train_df[train_df.Survived == 1].Sex.value_counts().values,
    text=train_df[train_df.Survived == 1].Sex.value_counts().values,
    textposition='auto',
    marker_color='#EF553B',
    showlegend=False,
    row=1, col=2
)

fig.update_layout(
    barmode='stack',
    height=400, width=1200,
)
fig.update_xaxes(ticks="inside")
fig.update_yaxes(ticks="inside", col=1)
fig.show()

Resulting plot:结果图: 使用 plotly 生成的预期堆积条形图

Hope this is helpful to the newbies of plotly like me.希望这对像我这样的plotly新手有所帮助。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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