在循环中绑定变量会改变其类型。

huangapple go评论70阅读模式
英文:

Binding variable in loop changes it's type

问题

我正在尝试整理一个使用nicegui的脚本。我使用一个字典来存储所有按钮标签以及它们将重定向到的页面。

我正在遍历pages字典中的所有键,并为每个键调用ui.button

from nicegui import ui

pages = {'page_one': '页面1', 'page_two': '页面2', 'page_three': '页面3'}

for page in pages:
    ui.button(pages[page], on_click=lambda page=page: ui.open(page))

当绑定page时,它变成了完全不同的类型nicegui.events.ClickEventArguments,而不是普通的字符串。

不绑定page会导致所有按钮重定向到page_three

ui.button(pages[page], on_click=lambda: ui.open(page))

我觉得我对绑定的实际含义以及lambda函数的操作方式有一些误解。

为什么在这个上下文中,page变量绑定到函数时会改变类型?

英文:

I'm trying to make some order in a script that uses nicegui. I'm using a dictionary to store all button labels and the pages they will redirect to.

I'm iterating over all keys in pages dictionary and calling ui.button for each of them.

from nicegui import ui

pages = {'page_one':'Page','page_two':'Page 2','page_three':'Page 3'}

for page in pages:
    ui.button(pages[page], on_click=lambda page=page: ui.open(page))

when binding page it becomes a completely different type nicegui.events.ClickEventArguments instead of a normal string

not binding page causes all buttons to redirect to page_three

ui.button(pages[page], on_click=lambda: ui.open(page))

I feel like I completely misunderstand what actually binding is and how lambdas operate.

Why is the page variable changing type when bound to function in this context?

答案1

得分: 3

NiceGUI会根据事件处理程序是否需要参数,自动传递事件参数。这样,您可以方便地编写类似以下代码,而不必担心可能的事件参数:

def do_something():
    ui.notify('Doing something...')

ui.button('Do something', on_click=do_something)

但您也可以接受和使用事件参数:

def show_value(value):
    ui.notify(value)

ui.input(on_change=lambda e: do_something(e.value))

现在,如果您像这样定义一个事件处理程序:lambda page=page: ui.open(page),NiceGUI会尝试将事件参数传递给page参数,因为lambda函数“期望”参数。为了避免用事件参数覆盖page参数,您可以插入另一个未使用的参数,通常用“_”表示,以吞噬事件参数同时保持page不变:lambda _, page=page: ui.open(page)

免责声明:我是NiceGUI的开发人员之一。我正在考虑NiceGUI是否能够检测到类似lambda page=page: ui.open(page)这样的情况,并且在所有函数参数已经具有默认值的情况下_不_传递事件参数。

英文:

NiceGUI automatically passes event arguments to event handlers - depending on whether they expect arguments or not. This way you can conveniently write something like

def do_something():
    ui.notify('Doing something...')

ui.button('Do something', on_click=do_something)

without caring about possible event arguments.

But you can also accept and consume event arguments:

def show_value(value):
    ui.notify(value)

ui.input(on_change=lambda e: do_something(e.value))

Now if you define an event handler like lambda page=page: ui.open(page), NiceGUI tries to pass event arguments to the page parameter, because the lambda function expects arguments. In order to avoid overwriting the page argument with event arguments, you can insert another unused parameter, commonly denoted with _, that swallows the event argument while keeping the page untouched: lambda _, page=page: ui.open(page).

Disclaimer: I'm one of the NiceGUI developers. And I'm thinking about whether NiceGUI could detect a case like lambda page=page: ui.open(page) and not passing event arguments, since all function parameters already have default values.

huangapple
  • 本文由 发表于 2023年5月28日 03:13:31
  • 转载请务必保留本文链接:https://go.coder-hub.com/76348605.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定