Streamlit滑块联动Plotly图表卡顿问题及优化求助
Streamlit中Plotly滑块图表响应慢的优化求助
问题场景
我在Streamlit中制作带响应滑块的正弦曲线图表时,发现拖动滑块时图表响应速度极慢。
初始实现代码(响应迟缓)
import numpy as np import plotly.graph_objects as go import streamlit as st if st.session_state.get('fig') is None: st.session_state['freq'] = np.arange(0.0, 5.1, 0.1).round(2) f = st.session_state['freq'][2] st.session_state['fig'] = go.Figure() st.session_state['fig'].add_trace( go.Scatter( name=str(f), x=np.arange(0, 10.01, 0.01), y=np.sin(f* np.arange(0, 10.01, 0.01)))) def sldier_callback(): f = st.session_state['slider_freq'] x = st.session_state['fig'].data[0].x st.session_state['fig'].data[0].y = np.sin(f*x) st.session_state['fig'].data[0].name = str(f) f = st.select_slider( label='Frequency', options=st.session_state['freq'], value=2, on_change=sldier_callback, key='slider_freq' ) st.plotly_chart(st.session_state['fig'])

Plotly原生高效实现对比
Plotly原生的滑块图表响应速度快很多,它的逻辑是初始化时创建所有图形并设置为隐藏,拖动滑块时仅切换对应图形的可见性。
原生实现代码
import plotly.graph_objects as go import numpy as np fig = go.Figure() for step in np.arange(0, 5, 0.1): fig.add_trace( go.Scatter( visible=False, name="f = " + str(step), x=np.arange(0, 10, 0.01), y=np.sin(step * np.arange(0, 10, 0.01)))) fig.data[10].visible = True # 创建并添加滑块 steps = [] for i in range(len(fig.data)): step = dict( method="update", args=[ {"visible": [False] * len(fig.data)}, {"title": "Slider switched to step: " + str(i)}], ) step["args"][0]["visible"][i] = True steps.append(step) sliders = [dict( active=10, currentvalue={"prefix": "Frequency: "}, pad={"t": 50}, steps=steps )] fig.update_layout( sliders=sliders ) fig.show()

复刻尝试仍未解决问题
我在Streamlit中复刻了Plotly原生的逻辑,但运行速度依然很慢,想请教有没有优化方案。
复刻实现代码
import streamlit as st import numpy as np import plotly.graph_objects as go if st.session_state.get('fig') is None: st.session_state['freq'] = np.arange(0.0, 5.01, 0.1).round(2) st.session_state['fig'] = go.Figure() for f in st.session_state['freq']: st.session_state['fig'].add_trace( go.Scatter( visible=False, name=str(f), x=np.arange(0, 10.01, 0.01), y=np.sin(f*np.arange(0, 10.01, 0.01)))) st.session_state['selected'] = 0 st.session_state['fig'].data[0].visible = True def sldier_callback(): i = st.session_state['selected'] st.session_state['fig'].data[i].visible = False freq = st.session_state['slider_freq'] i = np.where(st.session_state['freq']==freq)[0][0] st.session_state['fig'].data[i].visible = True st.session_state['selected'] = i f = st.select_slider( label='freq', options=st.session_state['freq'], value=2, on_change=sldier_callback, key='slider_freq' ) st.plotly_chart(st.session_state['fig'])
内容的提问来源于stack exchange,提问作者Scoodood
相关产品推荐
相关产品推荐

