如何通过dcc.Dropdown按REM值范围更新dash_table.DataTable
问题解决:根据下拉选项过滤Dash表格
核心问题在于你当前用字典存储了过滤后的条目,但回调需要的是对应条件的DataFrame,而不是字典。另外回调里的选项判断和下拉框的选项文字不匹配(比如下拉是"Expiring 1-5-days",你回调里写的是"Expiring 5-days"),这也会导致逻辑失效。
具体修改步骤:
- 替换字典存储为DataFrame过滤:不用手动循环遍历每一行,直接用Pandas的布尔索引快速过滤出符合条件的子集,代码更简洁高效。
- 修正回调的选项匹配:让回调里的判断值和下拉框的选项完全对应。
- 移除冗余代码:删掉原来的循环计数逻辑,用Pandas的
len()直接获取过滤后的行数。
修改后的完整代码
import os import datetime from dash_extensions.enrich import DashProxy from dash import dash_table, dcc, html from dash.dependencies import Input, Output import dash_bootstrap_components as dbc import pandas as pd os.system("") current_datetime = datetime.datetime.now() # 读取原始数据 df = pd.read_csv("testing_final_cert.csv") print(df.to_string()) # 直接用布尔索引过滤出各条件的DataFrame,替代原来的循环字典 df_0_days = df[df['REM'] <= 0] # Expired:REM≤0 df_5_days = df[(df['REM'] > 0) & (df['REM'] <= 5)] # Expiring 1-5-days:1≤REM≤5 df_10_days = df[(df['REM'] >= 6) & (df['REM'] <= 10)] # Expiring 6-10-days:6≤REM≤10 df_15_days = df[(df['REM'] >= 11) & (df['REM'] <= 15)] # Expiring 11-15-days:11≤REM≤15 # 统计各分类数量(如果需要保留统计逻辑) count_0_days = len(df_0_days) count_5_days = len(df_5_days) count_10_days = len(df_10_days) count_15_days = len(df_15_days) df_count_of_expiring_list = [["Expired", "5-days", "10-days", "15-days"], [count_0_days, count_5_days, count_10_days, count_15_days]] app = DashProxy(prevent_initial_callbacks=True) app.layout = html.Div([ dbc.Col(html.Div([ html.Label('Date filter'), dcc.Dropdown(id='date_filter_dropdown2', className="m-2", options=[{'label': i, 'value': i} for i in ["All", "Expired", "Expiring 1-5-days", "Expiring 6-10-days", "Expiring 11-15-days"]], searchable=True, value='All', placeholder='Select Expiration Date Filter from dropdown...', )]), width=6 ), dbc.Container([ dash_table.DataTable( data=df.to_dict('records'), columns=[{"name": i, "id": i} for i in df.columns], id='df_table_id', page_action="native", page_current=0, page_size=15, sort_action="native", sort_by=[{'column_id': 'REM', 'direction': 'asc'}], style_as_list_view=False, fixed_rows={'headers': False}, ), ], fluid=True), ]) @app.callback( Output(component_id='df_table_id', component_property='data'), Input(component_id='date_filter_dropdown2', component_property='value') ) def update_table(value): if value == 'All': return df.to_dict('records') elif value == 'Expired': return df_0_days.to_dict('records') elif value == 'Expiring 1-5-days': return df_5_days.to_dict('records') elif value == 'Expiring 6-10-days': return df_10_days.to_dict('records') elif value == 'Expiring 11-15-days': return df_15_days.to_dict('records') # 默认返回全量数据 return df.to_dict('records') if __name__ == '__main__': app.run_server(debug=True, host='0.0.0.0', port=7777)
关键改动说明:
- 用
df[df['REM'] <= 0]这种布尔索引直接生成过滤后的DataFrame,替代原来的循环遍历和字典存储,代码更简洁且性能更好。 - 回调函数里的判断条件和下拉框的选项文字完全对应(比如
'Expiring 1-5-days'),避免匹配失败。 - 移除了不必要的循环变量
counter,简化逻辑。
内容的提问来源于stack exchange,提问作者AliasSyed
相关产品推荐
相关产品推荐

