在Python中使用** kwargs的正确方法

当谈到默认值时,在Python中使用**kwargs的正确方法是什么?

kwargs返回一个字典,但是设置默认值的最佳方式是什么,或者是否有? 我应该只是作为字典来访问它? 使用get函数?

class ExampleClass:
    def __init__(self, **kwargs):
        self.val = kwargs['val']
        self.val2 = kwargs.get('val2')

一个简单的问题,但我无法找到很好的资源。 人们在我见过的代码中做了不同的方式,很难知道要使用什么。


您可以将默认值传递给不在字典中的键的get()

self.val2 = kwargs.get('val2',"default value")

但是,如果您打算使用特定默认值的特定参数,为什么不首先使用命名参数?

def __init__(self, val2="default value", **kwargs):

虽然大多数答案都是这样说的,例如,

def f(**kwargs):
    foo = kwargs.pop('foo')
    bar = kwargs.pop('bar')
    ...etc...

是相同的”

def f(foo=None, bar=None, **kwargs):
    ...etc...

这不是真的。 在后一种情况下, f可以称为f(23, 42)而前者的情况下接受名为唯一参数-没有位置的呼叫。 通常情况下,您希望允许调用者具有最大的灵活性,因此第二种形式(如大多数答案所声称的)是更可取的:但情况并非总是如此。 当你接受许多通常只有少数可选参数被传递的可选参数时,它可能是一个很好的主意(避免在你的呼叫站点发生事故和无法读取的代码!)来强制使用命名参数 - threading.Thread就是一个例子。 第一种形式是你如何在Python 2中实现它。

这个习语非常重要,在Python 3中它现在有特殊的支持语法:在def签名中的单个*之后的每个参数都是关键字,也就是说,不能作为位置参数传递,而只能作为命名参数传递。 所以在Python 3中,你可以将上面的代码编写为:

def f(*, foo=None, bar=None, **kwargs):
    ...etc...

事实上,在Python 3中,你甚至可以拥有不可选的关键字参数(没有缺省值的参数)。

然而,Python 2仍然具有长期的生产力,因此最好不要忘记使用Python 3实现的技术和习惯用法,这是Python 3中语言直接支持的重要设计思想!


我建议这样的事情

def testFunc( **kwargs ):
    options = {
            'option1' : 'default_value1',
            'option2' : 'default_value2',
            'option3' : 'default_value3', }

    options.update(kwargs)
    print options

testFunc( option1='new_value1', option3='new_value3' )
# {'option2': 'default_value2', 'option3': 'new_value3', 'option1': 'new_value1'}

testFunc( option2='new_value2' )
# {'option1': 'default_value1', 'option3': 'default_value3', 'option2': 'new_value2'}

然后以任何你想要的方式使用这些值

dictionaryA.update(dictionaryB)增加的内容dictionaryBdictionaryA覆盖任何重复键。

链接地址: http://www.djcxy.com/p/18171.html

上一篇: Proper way to use **kwargs in Python

下一篇: Why sorted(dictionary) returns a list instead of dictionary?