Python中Dash库代码流程入门

Dash简介

Dash 是一个用于构建基于 Web 的应用程序的 Python 库,无需 JavaScript

Dash 同时也是用于创建分析 Web 应用程序的用户界面库。那些使用 Python 进行数据分析、数据挖掘、可视化、建模、仪器控制和报告的人可以立即使用 Dash

Dash 建立在 Plotly.js、React 和 Flask 之上,将现代 UI 元素(如下拉列表、滑块和图形)与你的分析 Python 代码相结合

直接上代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
import dash
import dash_core_components as dcc
import dash_html_components as html
from dash.dependencies import Input, Output
import plotly.express as px

import pandas as pd

external_stylesheets = ['https://codepen.io/chriddyp/pen/bWLwgP.css']

app = dash.Dash(__name__, external_stylesheets=external_stylesheets)

df = pd.read_csv('https://plotly.github.io/datasets/country_indicators.csv')

available_indicators = df['Indicator Name'].unique()

app.layout = html.Div([
html.Div([

html.Div([
dcc.Dropdown(
id='x_axis-column',
options=[{'label': i, 'value': i} for i in available_indicators],
value='Fertility rate, total (births per woman)'
),
dcc.RadioItems(
id='x_axis-type',
options=[{'label': i, 'value': i} for i in ['Linear', 'Log']],
value='Linear',
labelStyle={'display': 'inline-block'}
)
],
style={'width': '48%', 'display': 'inline-block'}),

html.Div([
dcc.Dropdown(
id='yaxis-column',
options=[{'label': i, 'value': i} for i in available_indicators],
value='Life expectancy at birth, total (years)'
),
dcc.RadioItems(
id='yaxis-type',
options=[{'label': i, 'value': i} for i in ['Linear', 'Log']],
value='Linear',
labelStyle={'display': 'inline-block'}
)
], style={'width': '48%', 'float': 'right', 'display': 'inline-block'})
]),

dcc.Graph(id='indicator-graphic'),

dcc.Slider(
id='year--slider',
min=df['Year'].min(),
max=df['Year'].max(),
value=df['Year'].max(),
marks={str(year): str(year) for year in df['Year'].unique()},
step=None
)
])


@app.callback(
Output('indicator-graphic', 'figure'),
Input('x_axis-column', 'value'),
Input('yaxis-column', 'value'),
Input('x_axis-type', 'value'),
Input('yaxis-type', 'value'),
Input('year--slider', 'value'))
def update_graph(x_axis_column_name, yaxis_column_name,
x_axis_type, yaxis_type,
year_value):
dff = df[df['Year'] == year_value]

fig = px.scatter(x=dff[dff['Indicator Name'] == x_axis_column_name]['Value'],
y=dff[dff['Indicator Name'] == yaxis_column_name]['Value'],
hover_name=dff[dff['Indicator Name'] == yaxis_column_name]['Country Name'])

fig.update_layout(margin={'l': 40, 'b': 40, 't': 10, 'r': 0}, hovermode='closest')

fig.update_xaxes(title=x_axis_column_name,
type='linear' if x_axis_type == 'Linear' else 'log')

fig.update_yaxes(title=yaxis_column_name,
type='linear' if yaxis_type == 'Linear' else 'log')

return fig


if __name__ == '__main__':
app.run_server(debug=True)

代码分析

导入

导入

这是最常见的导入模块,常常和pandas一起使用

dash包:用来实例化app的包

pandas:用来读取数据

dash_core_components:Dash自定义了一些前端框架,比如:下拉框,滑动条等一些交互组件

dash_html_components:dash用来构建前端基础代码标签,比如:Div,H1,Tr等前端标签

plotly:用来画图

实例化app

1
app = dash.Dash(__name__, external_stylesheets=external_stylesheets)

获取数据

1
df = pd.read_csv('https://plotly.github.io/datasets/country_indicators.csv')

布局

交互布局
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
html.Div([
dcc.Dropdown(
id='x_axis-column',
options=[{'label': i, 'value': i} for i in available_indicators],
value='Fertility rate, total (births per woman)'
),
dcc.RadioItems(
id='x_axis-type',
options=[{'label': i, 'value': i} for i in ['Linear', 'Log']],
value='Linear',
labelStyle={'display': 'inline-block'}
)],
style={'width': '48%', 'display': 'inline-block'}
),
html.Div([
dcc.Dropdown(
id='yaxis-column',
options=[{'label': i, 'value': i} for i in available_indicators],
value='Life expectancy at birth, total (years)'
),
dcc.RadioItems(
id='yaxis-type',
options=[{'label': i, 'value': i} for i in ['Linear', 'Log']],
value='Linear',
labelStyle={'display': 'inline-block'}
)],
style={'width': '48%', 'float': 'right', 'display': 'inline-block'}
)

1、交互框位于dash_core_components包中

2、支持MarkDown语法,调用dcc.Markdown方法

3、有下拉框、单选框、复选框、输入框、文本框、滑动条等组件

图标布局

1、图表标签位于dash_core_components包中

1
dcc.Graph(id='indicator-graphic')
页面布局

1、布局与前端HTML代码类似的树形结构

2、HTML标签的首字母大写

3、每一个标签都有id,children,style属性

4、将被嵌套的标签放到children中,如果有多个,就用放到list中

1
2
3
4
5
6
7
8
dcc.Slider(
id='year--slider',
min=df['Year'].min(),
max=df['Year'].max(),
value=df['Year'].max(),
marks={str(year): str(year) for year in df['Year'].unique()},
step=None
)

添加Callbacks

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
@app.callback(
Output('indicator-graphic', 'figure'),
Input('x_axis-column', 'value'),
Input('yaxis-column', 'value'),
Input('x_axis-type', 'value'),
Input('yaxis-type', 'value'),
Input('year--slider', 'value'))
def update_graph(x_axis_column_name, yaxis_column_name,
x_axis_type, yaxis_type,
year_value):
dff = df[df['Year'] == year_value]

fig = px.scatter(x=dff[dff['Indicator Name'] == x_axis_column_name]['Value'],
y=dff[dff['Indicator Name'] == yaxis_column_name]['Value'],
hover_name=dff[dff['Indicator Name'] == yaxis_column_name]['Country Name'])

fig.update_layout(margin={'l': 40, 'b': 40, 't': 10, 'r': 0}, hovermode='closest')

fig.update_xaxes(title=x_axis_column_name,
type='linear' if x_axis_type == 'Linear' else 'log')

fig.update_yaxes(title=yaxis_column_name,
type='linear' if yaxis_type == 'Linear' else 'log')

return fig

1、此处为多输入单输出

2、输入输出值注意和之前的id对应

效果展示

静态展示

GIF展示