为什么非默认参数不能遵循默认参数?

dot*_*ash 118 python

为什么这段代码会抛出一个SyntaxError?

  >>> def fun1(a="who is you", b="True", x, y):
...     print a,b,x,y
... 
  File "<stdin>", line 1
SyntaxError: non-default argument follows default argument
Run Code Online (Sandbox Code Playgroud)

虽然下面的代码运行没有可见的错误:

>>> def fun1(x, y, a="who is you", b="True"):
...     print a,b,x,y
... 
Run Code Online (Sandbox Code Playgroud)

Rah*_*tam 143

所有必需参数必须放在任何默认参数之前.仅仅因为它们是强制性的,而默认参数则不是.从语法上讲,如果允许混合模式,解释器将无法确定哪些值与哪些参数匹配.SyntaxError如果没有以正确的顺序给出参数,则引发A :

让我们使用您的函数来查看关键字参数.

def fun1(a="who is you", b="True", x, y):
...     print a,b,x,y
Run Code Online (Sandbox Code Playgroud)

假设它允许声明如上所述的函数,然后使用上面的声明,我们可以进行以下(常规)位置或关键字参数调用:

func1("ok a", "ok b", 1)  # Is 1 assigned to x or ?
func1(1)                  # Is 1 assigned to a or ?
func1(1, 2)               # ?
Run Code Online (Sandbox Code Playgroud)

如何在函数调用中建议变量的赋值,如何使用默认参数以及关键字参数.

>>> def fun1(x, y, a="who is you", b="True"):
...     print a,b,x,y
... 
Run Code Online (Sandbox Code Playgroud)

参考O'Reilly - Core-Python
这个函数在上面的函数调用中使用语法正确的默认参数.关键字参数调用证明对于能够提供无序位置参数很有用,但是,与默认参数一起,它们也可以用于"跳过"缺少的参数.

  • &lt;q&gt;在语法上,如果允许混合模式,解释器将无法决定哪些值与哪些参数匹配。&lt;/q&gt; Ruby 允许在默认参数之后使用非默认参数。&lt;q&gt;您将如何建议在函数调用中分配变量&lt;/q&gt; 只需使用 `func1(x=1, y=2)`。 (8认同)
  • 你为什么要写“在语法上,如果允许混合模式,解释器就不可能决定哪些值与哪些参数匹配。”?我认为 [PEP 3102](https://www.python.org/dev/peps/pep-3102/#function-calling-behavior) 的算法可以完全相同,即使 `def foo(x=None , y)` 将被允许。所以我仍然很好奇 * 为什么 * Python 不允许这样做。是否有真正的根本原因,或者只是“我们不允许,因为我们不允许”。 (5认同)
  • 尝试使用“def foo(a = 1,b):通过foo(b = 2)调用”并告诉我pep在哪里抛出,我猜这不是在非默认值之前禁止默认值的原因。 (2认同)

jam*_*lak 13

SyntaxError: non-default argument follows default argument
Run Code Online (Sandbox Code Playgroud)

如果你允许这样做,那么默认参数将变得无用,因为你永远无法使用它们的默认值,因为非默认参数来自之后.

但是,在Python 3中,您可以执行以下操作:

def fun1(a="who is you", b="True", *, x, y):
    pass
Run Code Online (Sandbox Code Playgroud)

这使得xy只有这样你就可以做到这一点关键字:

fun1(x=2, y=2)
Run Code Online (Sandbox Code Playgroud)

这是有效的,因为不再有任何歧义.请注意,您仍然无法做到fun1(2, 2)(这将设置默认参数).

  • 这是不正确的:“如果您允许这样做,默认参数将变得无用,因为您将永远无法使用它们的默认值,因为非默认参数在后面。” 示例: def foo(a=1 ,b):通过 foo(b=2) 调用 (2认同)

Aad*_*Ura 10

我在这里澄清两点:

  • 首先非默认参数不应该遵循默认参数,这意味着你不能在函数中定义(a = b,c)函数中定义参数的顺序是:
    • 位置参数或非默认参数即(a,b,c)
    • 关键字参数或默认参数即(a ="b",r ="j")
    • 仅关键字参数ie(*args)
    • var-keyword参数即(**kwargs)

def example(a, b, c=None, r="w" , d=[], *ae, **ab):

(a,b)是位置参数

(c =无)是可选参数

(r ="w")是关键字参数

(d = [])是列表参数

(*ae)仅限关键字

(**ab)是var-keyword参数

  • 现在次要的事情是,如果我尝试这样的事情: def example(a, b, c=a,d=b):

保存默认值时未定义参数,Python在您定义函数时计算并保存默认值

c和d未定义,不存在,何时发生(仅在执行函数时存在)

"a,a = b"在参数中不允许.