kwargs 是按值传递还是解压 dict 复制数据?

Does kwargs is passed by value or does unpacking dict copies data?

提问人:alexsmail 提问时间:11/19/2020 最后编辑:alexsmail 更新时间:11/19/2020 访问量:262

问:

最好通过例子来说明我的问题。 假设我有以下代码:

from pprint import pprint

def remove(**kwargs):
    del kwargs['first']


d = {'first': {'x': 10}, 'second': {'a': '1'}}
logger.debug(f"{pprint(d)}")
remove(**d)
logger.debug(f"{pprint(d)}")

输出为:

{'first': {'x': 10}, 'second': {'a': '1'}}

{'first': {'x': 10}, 'second': {'a': '1'}}

也就是说,键仍然存在,就好像我们已经通过值传递了我们的 dict d,因此函数内部对它的任何更改对调用者都是不可见的。'first'

我希望我的 d 通过引用传递,也就是说我的字典被修改了,我希望看到以下输出:

{'first': {'x': 10}, 'second': {'a': '1'}}

{'second': {'a': '1'}}

为什么我错了?

python 传递 关键字参数

评论


答:

1赞 B. Morris 11/19/2020 #1

您不是在传递给函数,而是将值从命名参数扩展到函数。在所讨论的函数中,您将再次将它们作为字典接收,但是如果您要将值作为命名参数传递或作为命名参数接收值,则这些值将分别来自或最终出现在字典中。dd

例如,如果您可以修改 的来源,在这种情况下这意味着什么?**kwargs

remove(first={'x': 10}, second={'a': '1'})

这真的没有意义。

如果要完成函数名称所暗示的操作,则需要直接将字典对象作为参数传递;然后它将通过引用和函数中的修改将按您的预期工作。

def remove(dictarg):
    del dictarg['first']
d = {'first': {'x': 10}, 'second': {'a': '1'}}
remove(d)
pprint(d)

>>> {'second': {'a': '1'}}

评论

0赞 alexsmail 11/19/2020
谢谢。那么,这里发生了什么,我的正在扩展为函数的命名参数并“分离”它?d