【问题标题】:Inputs in Chained Call backs - dash链式回调中的输入 - 破折号
【发布时间】:2021-10-14 03:17:51
【问题描述】:

是否可以向另一个回调中的回调函数提供输入?在下面的示例中,我需要处理从 for 循环中的外部回调函数传递的每个 dict_item['Name']。

# Outer Call back
@app.callback(
    dash.dependencies.Output("dummydiv", "children"),  # Dummy Output
    [dash.dependencies.Input("interval1", "n_intervals")],  # Interal Triger
    [dash.dependencies.Input("table", "data")],
)  # dcc.Store which stores values
def use_table(n, data):
    print(type(data))
    print("Outer Called")

    if data:
        for dict_item in data:

            @app.callback(
                dash.dependencies.Output(
                    "lable1", "children"
                ),  # Output to print the values in a llop
                dash.dependencies.Input(dict_item["Name"]),
            )
            def printing(s_name):

                sn = s_name
                print(sn)

                return sn  # Return "Name to Print" to id "Lable1"

        return ""  # Dummy String  - Print Nothing to id "dummydiv"
    return dash.no_update

很遗憾,我无法将输入参数传递给内部回调函数。它返回以下错误:

dash.dependencies.Input(dict_item['Name]) 类型错误:init() 缺少 1 个必需的位置参数:'component_property'

如何将变量从外部回调传递给内部回调?或者有没有其他可能的方式来实现这个逻辑?

编辑:可重现的代码

import dash
import dash_core_components as dcc
import dash_html_components as html
import dash_table
from dash.dependencies import Output, Input, State
from datetime import datetime

user_key = "Name"
# Setup table.
columns = ["Name", "Age", "Place", "Vaccinated"]

table = dash_table.DataTable(
    columns=[{"name": column, "id": column} for column in columns], data=[], id="table"
)
# Create app.


app = dash.Dash(prevent_initial_callbacks=True)
app.layout = html.Div(
    [
        html.Div(
            [dcc.Input(id=column, value=column) for column in columns]
            + [html.Button("Save", id="save"), dcc.Store(id="cache", data=[]), table]
        ),
        html.Div(
            [
                dcc.Interval(id="interval1", interval=5 * 1000, n_intervals=0),
                html.H1(id="dummydiv", children=""),
                html.H1(id="label1", children=""),
            ]
        ),
    ]
)


@app.callback(
    Output("table", "data"),
    [Input("save", "n_clicks")],
    [State("table", "data")] + [State(column, "value") for column in columns],
)
def update_table(n_clicks, data, *args):
    record = {columns[i]: arg for i, arg in enumerate(list(args))}
    # If the record (identified by user_key) already exists, update it.
    try:
        record_index = [record[user_key] for record in data].index(record[user_key])
        data[record_index] = record
    # Otherwise, append it.
    except ValueError:
        data.append({columns[i]: arg for i, arg in enumerate(list(args))})
    # Return the updated data.
    return data


@app.callback(
    dash.dependencies.Output("label1", "children"),
    [dash.dependencies.Input("interval1", "n_intervals")],
    [dash.dependencies.Input("table", "data")],
)
def use_table(n, data):
    print(type(data))
    if data:
        for dict_item in data:

            print(dict_item["Name"])
            # for key in dict_item:
            #     print (dict_item[key])

            return dict_item["Name"]


if __name__ == "__main__":
    app.run_server()

简而言之,上面的应用程序允许用户输入某些值并在下面显示一个表格并存储输入的数据。我需要显示在循环中从列Name 检索到ID 为lable1 的输出组件的值(一次一个名称,而不是list)。由于在回调函数force中添加return语句会退出``for循环`,所以我使用了嵌套回调逻辑。

【问题讨论】:

    标签: python plotly plotly-dash dashboard


    【解决方案1】:

    短划线输入需要将值传递给component_idcomponent_property 参数。

    正如错误告诉你的那样,你只是通过了一个:

    缺少 1 个必需的位置参数:'component_property'

    将内部回调的语法与外部回调的语法进行比较。

    说了这么多,don't nest callbacks in the first place。预先定义回调。


    根据编辑更新

    我需要显示从列名称循环检索到 ID 为 lable1 的输出组件的值(一次一个名称,而不是列表)。由于在回调函数中加了return语句force退出了for循环。

    您不需要立即在循环中返回某些内容。您可以先建立值列表,然后再返回。您可以在迭代时初始化一个列表并将元素附加到该列表,或者您可以使用list comprehension 并执行以下操作:

    @app.callback(
        dash.dependencies.Output("label1", "children"),
        [dash.dependencies.Input("interval1", "n_intervals")],
        [dash.dependencies.Input("table", "data")],
    )
    def use_table(n, data):
        return ", ".join([dict_item["Name"] for dict_item in data])
    

    这会显示每行的所有名称,使用列表推导以逗号和空格分隔,无需嵌套回调。根据您要显示的内容进行调整。

    【讨论】:

    • 明白了!!但是有没有办法将dict_item['Name'] 的值传递给内部回调函数?
    • 您需要提供更多详细信息(代码以及您正在尝试做什么)。不要嵌套回调,回调一般应该预先定义。
    • 很抱歉没有解释清楚。我有一个dcc.store 存储某些数据,其中一列是Name。我只想遍历数据存储并在输出标头组件中显示具有 id lable1 的名称。当然,这会在一定的时间间隔后重复,因此使用输入组件interval1
    • 如果我对您的理解正确,您可以将 lable1 设为外部回调的 Output,删除嵌套回调并返回您希望输出基于 data 的内容。
    • 我已经添加了可重现的代码,希望现在更清楚。请帮忙。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-05-01
    • 1970-01-01
    • 2021-10-19
    • 1970-01-01
    • 2019-06-09
    • 1970-01-01
    • 2020-11-09
    相关资源
    最近更新 更多