Python 功能:**kwargs允许不正确命名的变量

Python 功能:**kwargs允许不正确命名的变量,python,python-2.x,Python,Python 2.x,以下内容无效: def myInvalidFun(kw arg zero=6): pass def myValidFun(**kwargs): if kwargs.has_key("kw arg zero"): pass 以下是有效的python: def myInvalidFun(kw arg zero=6): pass def myValidFun(**kwargs): if kwargs.has_key("kw arg zero"):

以下内容无效:

def myInvalidFun(kw arg zero=6):
    pass
def myValidFun(**kwargs):
    if kwargs.has_key("kw arg zero"):
        pass
以下是有效的python:

def myInvalidFun(kw arg zero=6):
    pass
def myValidFun(**kwargs):
    if kwargs.has_key("kw arg zero"):
        pass
然而,调用
myValidFun
是一件棘手的事情。例如,以下几种方法不起作用:

myValidFun(kw arg zero=6)      # SyntaxError: invalid syntax
myValidFun("kw arg zero"=6)    # SyntaxError: keyword can't be an expression

kwargs = dict("kw arg zero"=6) # SyntaxError: keyword can't be an expression 
myValidFun(**kwargs)
(也许与前两个相同的错误暗示了引擎盖下发生了什么?)但是,这确实有效:

kwargs = {"kw arg zero": 6}
myValidFun(**kwargs)
考虑到创建字典的{:}语法,是否有特别的原因使myValidFun(“kw arg zero”=6)无效

(更多背景:我有一个非常像字典的类,只是有大量的验证,还有一个
\uuuuu init\uuuu
,它使用字典的条目构建一个容器,但不是字典……它实际上是一个XML元素树,在某些方面类似于列表,在另一些方面类似于dict方法必须像“我的第一个元素”和“MyFixStILL元素”这样的键,并把它们看作不同的东西。类和 编辑:我理解标识符的概念,我的无效代码就是为了说明这一点。我想我的问题应该改为:

为什么以下内容有效

myValidFun(**{"invalid identifier":6})

python函数的关键字必须是有效标识符。这是因为另一方面,它们需要解压为标识符(变量):

您拥有的大多数东西都不是有效的标识符:

kw arg zero  #Not valid identifier -- Can't have spaces
"kw arg zero" #Not valid identifier -- It's parsed as a string (expression)

dict("kw arg zero" = 6)
对于解析器来说,与

myValidFunc("kw arg zero" = 6)


正如您所指出的,您可以传递things视图映射打包/解包(
**kwargs
)。但是,它只能通过字典访问。

python函数的关键字必须是有效标识符。这是因为另一方面,它们需要解包为标识符(变量):

您拥有的大多数东西都不是有效的标识符:

kw arg zero  #Not valid identifier -- Can't have spaces
"kw arg zero" #Not valid identifier -- It's parsed as a string (expression)

dict("kw arg zero" = 6)
对于解析器来说,与

myValidFunc("kw arg zero" = 6)

现在正如您所指出的,您可以传递things视图映射打包/解包(
**kwargs
)。但是,它只能通过字典访问。

myInvalidFun(kw arg zero=6):
无效,因为不允许使用空格

myValidFun(“kw arg zero”=6)
无效,因为函数希望关键字是有效的变量名而不是字符串。类似于
“kw arg zero”=6
的内容也无效,因为无法为字符串赋值

dict(“kw arg zero”=6)
:同上。顺便说一句
dict()
接受(键、值)对或iterable

这是有效的,因为您只在此处传递了dict,dict可以将字符串作为带空格的键

def myValidFun(**kwargs): #using ** here simply packs the dictionary again
        pass
myValidFun(**{"invalid identifier":6})
这是有效的,因为您在函数定义中使用了有效的标识符

def myValidFun( foo = 5):  #foo from dict replaces it's default value
    print foo               #prints 6
myValidFun(**{"foo":6}) 
无效:

def myValidFun(foo bar = 5): # syntax error, invalid identifier
    print foo
myValidFun(**{"foo bar":6})    
    
myInvalidFun(kw arg zero=6):
无效,因为不允许在中使用空格

myValidFun(“kw arg zero”=6)
无效,因为函数希望关键字是有效的变量名而不是字符串。类似于
“kw arg zero”=6
的内容也无效,因为无法为字符串赋值

dict(“kw arg zero”=6)
:同上。顺便说一句
dict()
接受(键、值)对或iterable

这是有效的,因为您只在此处传递了dict,dict可以将字符串作为带空格的键

def myValidFun(**kwargs): #using ** here simply packs the dictionary again
        pass
myValidFun(**{"invalid identifier":6})
这是有效的,因为您在函数定义中使用了有效的标识符

def myValidFun( foo = 5):  #foo from dict replaces it's default value
    print foo               #prints 6
myValidFun(**{"foo":6}) 
无效:

def myValidFun(foo bar = 5): # syntax error, invalid identifier
    print foo
myValidFun(**{"foo bar":6})    
    

密钥名不能有空格。 通过在函数调用中的参数周围加引号,可以计算表达式

试试这个

def myValidFun(**kwargs):
    if "kw_arg_zero" in kwargs:
        print kwargs["kw_arg_zero"]


myValidFun(kw_arg_zero="whatever")

密钥名不能有空格。 通过在函数调用中的参数周围加引号,可以计算表达式

试试这个

def myValidFun(**kwargs):
    if "kw_arg_zero" in kwargs:
        print kwargs["kw_arg_zero"]


myValidFun(kw_arg_zero="whatever")

将数据作为关键字参数传递:data={…}as space作为参数名无效。这听起来更安全。我的意思是,我知道最后一个有效的snip与我当前的python实现一起工作,但对我来说似乎有点粗略。感谢您的建议。将数据作为关键字参数传递:data={…}因为空格不能作为参数名。这听起来更安全。我的意思是,我知道最后一个有效的snip可以在我当前的python实现中使用,但对我来说似乎有点粗略。谢谢你的建议。对,我明白了,虽然我没有考虑dict()的情况作为一个接受**kwargs参数的函数,这现在就很有意义了。但是为什么
myValidFunc(**{“kw arg zero”:6})
valid?创建的结果字典中有一个键不是有效的标识符,对吗?我仍然觉得我遗漏了一些明显的东西…@Ethacoon--是的,它是一个无效的标识符,但是,它永远不能作为标识符在另一边解包,只能作为
kwargs
字典的一部分。@Ethacoon--有趣的是eno呃,我在规范中找不到任何地方实际表明这种行为是允许的。我找到的最好的方法是只讨论有效标识符。这可能是依赖于实现的行为(但我需要搜索更多才能确定)。嗯,好的。“它不在规范中,解释器的未定义行为也不在规范中,所以你很幸运“我的答案是可以的。我会等一会儿看是否还有其他评论/答案,但如果你在答案中编辑了这样的内容,我会检查一下。谢谢!@EthanCoon--嗯……我会比这里更小心一点……在“规范中找不到”和“规范中没有”之间有区别”:-P.好的,我明白了,虽然我没有想到dict()是一个接受**kwargs参数的函数,但现在这很有意义。但是为什么
myValidFunc(**{“kw arg zero”:6})
有效?创建的字典有一个键不是有效的标识符,对吗?我仍然觉得我是个