我希望用户能够在给定的 plotly html 导出/绘图中动态分析数据。 基于图中当前显示的值,我想显示一些数据统计信息,如平均值、标准差、最小值/最大值。
使用这段代码,我可以生成一个显示正弦波的图。 现在我想动态调整“标题”(或另一个注释)以显示当前显示数据的统计信息。
import plotly.graph_objects as go
import numpy as np
# Generate some sample data
x = np.linspace(0, 2 * np.pi, 1000)
y = np.sin(x)
# Calculate the statistics
avg = np.mean(y)
min_val = np.min(y)
max_val = np.max(y)
# Create the plot
fig = go.Figure(
data=go.Scatter(x=x, y=y),
layout=go.Layout(
title=f'Sine Waveform\nAverage: {avg:.2f}, Min: {min_val:.2f}, Max: {max_val:.2f}',
xaxis=dict(title='x'),
yaxis=dict(title='y')
)
)
# Show the plot
fig.show()
使用
plotly-dash
的解决方案也可以。
您可以使用支持
回调的
plotly-dash
。我们可以创建一个回调函数,将图形的布局数据作为输入,修改图形的标题,并在用户缩放时实时将图形输出到应用程序(还有一种边缘情况,我们会重置图形以及用户刷新页面时的标题)。
下面是一个工作代码示例:
from dash import Dash, dcc, html, Input, Output
import plotly.graph_objects as go
import numpy as np
import pandas as pd
app = Dash(__name__)
# Generate some sample data
x = np.linspace(0, 2 * np.pi, 1000)
y = np.sin(x)
# Calculate the statistics
avg = np.mean(y)
min_val = np.min(y)
max_val = np.max(y)
df = pd.DataFrame({'x':x, 'y':y})
# Create the plot
fig = go.Figure(
data=go.Scatter(x=x, y=y),
layout=go.Layout(
title=f'Sine Waveform\nAverage: {avg:.2f}, Min: {min_val:.2f}, Max: {max_val:.2f}',
xaxis=dict(title='x'),
yaxis=dict(title='y')
)
)
app.layout = html.Div(
[dcc.Graph(figure=fig, id='scatter-chart')]
)
@app.callback(
Output('scatter-chart', 'figure'),
Input('scatter-chart', 'relayoutData'),
prevent_initial_call=True,
)
def update_title(relayout_data):
try:
x_min, x_max = relayout_data['xaxis.range[0]'], relayout_data['xaxis.range[1]']
y_min, y_max = relayout_data['yaxis.range[0]'], relayout_data['yaxis.range[1]']
except:
avg = np.mean(y)
min_val = np.min(y)
max_val = np.max(y)
y_pad = (max_val-min_val)/16
fig.update_layout(
xaxis_range=[min(x), max(x)],
yaxis_range=[min(y)-y_pad, max(y)+y_pad],
title=f'Sine Waveform\nAverage: {avg:.2f}, Min: {min_val:.2f}, Max: {max_val:.2f}'
)
return fig
df_subset = df[
df['x'].between(x_min,x_max) &
df['y'].between(y_min,y_max)
]
avg = df_subset['y'].mean()
min_val, max_val = df_subset['y'].min(), df_subset['y'].max()
fig.update_layout(
xaxis_range=[x_min, x_max],
yaxis_range=[y_min, y_max],
title=f'Sine Waveform\nAverage: {avg:.2f}, Min: {min_val:.2f}, Max: {max_val:.2f}'
)
return fig
if __name__ == '__main__':
app.run_server(debug=True)