Plotly Python使用按钮过滤数据点击下拉框后数值异常问题问询
Plotly下拉筛选功能异常原因及修复方案
问题原因
你代码的核心问题是visible参数对应的布尔列表长度和图表实际包含的trace数量不匹配:
- 每个国家对应2条Bar trace(Coal、Gas各1条),3个国家总共生成了6条trace
- 原有代码构造的显隐控制列表
args = [False] * len(df_dict)长度仅为3,和6条trace的数量不匹配,点击下拉按钮时仅能控制前3条trace的显隐,剩余trace的显隐逻辑完全错误,最终导致切换国家后图表数值不符合预期。
修复方案
调整显隐控制列表的构造逻辑,保证其长度和总trace数一致,对应每个国家的2条trace同步控制显隐即可,修正后的完整代码如下:
import pandas as pd import plotly.graph_objects as go #Dummy data df_germany = pd.DataFrame({'Fuels':[2010,2011],'Coal':[200,250],'Gas':[400,500]}) df_poland = pd.DataFrame({'Fuels':[2010,2011],'Coal':[500,150],'Gas':[600,100]}) df_spain = pd.DataFrame({'Fuels':[2010,2011],'Coal':[700,260],'Gas':[900,400]}) #put dataframes into object for easy access: df_dict = {'Germany': df_germany, 'Poland': df_poland, 'Spain': df_spain} #每个国家对应的trace数量,此处为2种燃料 trace_per_country = len(df_germany.columns) -1 #总trace数量 total_trace = len(df_dict) * trace_per_country #create a figure from the graph objects (not plotly express) library fig = go.Figure() buttons = [] i = 0 #iterate through dataframes in dict for country, df in df_dict.items(): #iterate through columns in dataframe (not including the year column) for column in df.drop(columns=['Fuels']): #add a bar trace to the figure for the country we are on fig.add_trace(go.Bar( name = column, #x axis is "fuels" where dates are stored as per example x = df.Fuels.to_list(), #y axis is the data for the column we are on y = df[column].to_list(), #setting only the first country to be visible as default visible = (i==0) ) ) #args长度改为总trace数,初始全为False args = [False] * total_trace #将当前国家对应的2个trace设为可见 args[trace_per_country*i : trace_per_country*(i+1)] = [True]*trace_per_country #create a button object for the country we are on button = dict(label = country, method = "update", args=[{"visible": args}]) #add the button to our list of buttons buttons.append(button) #i is an iterable used to tell our "args" list which value to set to True i+=1 fig.update_layout( updatemenus=[ dict( #change this to "buttons" for individual buttons type="dropdown", #this can be "left" or "right" as you like direction="down", #(1,1) refers to the top right corner of the plot x = 1, y = 1, #the list of buttons we created earlier buttons = buttons) ], #stacked bar chart specified here barmode = "stack", #so the x axis increments once per year xaxis = dict(dtick = 1)) fig.show()
运行修正后的代码,点击下拉按钮切换国家即可得到符合预期的堆叠柱状图。
内容的提问来源于stack exchange,提问作者Hongyi Chen
相关产品推荐
相关产品推荐

