help() 列出方法签名时斜线是什么意思?

问题描述 投票:0回答:3

/
在 Python 3.4 的
help
输出中对于右括号前的
range
是什么意思?

>>> help(range)
Help on class range in module builtins:

class range(object)
 |  range(stop) -> range object
 |  range(start, stop[, step]) -> range object
 |  
 |  Return a virtual sequence of numbers from start to stop by step.
 |  
 |  Methods defined here:
 |  
 |  __contains__(self, key, /)
 |      Return key in self.
 |  
 |  __eq__(self, value, /)
 |      Return self==value.

                                        ...
python python-3.x parameters introspection
3个回答
296
投票

它表示仅位置参数,您不能用作关键字参数的参数。在 Python 3.8 之前,此类参数只能在 C API 中指定。

这意味着

key
__contains__
参数只能按位置传递 (
range(5).__contains__(3)
),而不是作为关键字参数 (
range(5).__contains__(key=3)
),您可以 在纯 python 函数中使用位置参数.

另请参阅 Argument Clinic 文档:

要在 Argument Clinic 中将所有参数标记为仅位置参数,请在最后一个参数之后单独在一行上添加一个

/
,缩进与参数行相同。

和(最近添加的)Python FAQ

函数参数列表中的斜杠表示它之前的参数是位置参数。仅位置参数是没有外部可用名称的参数。在调用接受仅位置参数的函数时,参数仅根据其位置映射到参数。

语法现在是 Python 语言规范的一部分,从版本 3.8 开始,请参阅PEP 570 – Python Positional-Only Parameters。在 PEP 570 之前,该语法已被保留以备将来可能包含在 Python 中,请参阅PEP 457 - Positional-Only Parameters 的语法

仅位置参数可以使 API 更干净、更清晰,使其他纯 C 模块的纯 Python 实现更加一致且更易于维护,并且由于仅位置参数需要很少的处理,因此它们会导致更快的 Python 代码。


83
投票

这个问题是我自己问的。 :) 发现

/
最初是由Guido在here提出的。

备选方案:使用 '/' 怎么样?这有点相反 '*' 的意思是“关键字参数”,而 '/' 不是新字符。

然后他的提议赢了.

呵呵。如果那是真的,我的 '/' 提案获胜:

 def foo(pos_only, /, pos_or_kw, *, kw_only): ...

我认为与此相关的文件是PEP 570。 回顾部分看起来不错。

回顾

用例将决定在函数定义中使用哪些参数:

 def f(pos1, pos2, /, pos_or_kwd, *, kwd1, kwd2):

作为指导:

如果名称无关紧要或没有意义,并且只有少数参数将始终以相同顺序传递,则仅使用位置。 仅当名称有意义并且函数定义通过名称显式更容易理解时才使用关键字。


如果函数以

/

结束
def foo(p1, p2, /)

这意味着所有功能参数都是位置性的。


33
投票

正斜杠 (/) 表示它之前的所有参数都是位置参数。在 PEP 570 被接受后,python 3.8 中添加了仅位置参数功能。最初这个符号是在 PEP 457 - Positional-Only Parameters 的符号

中定义的

函数定义中前斜杠 (/) 之前的参数只是位置参数,后跟斜杠 (/) 的参数可以是任何类型的语法。其中参数仅根据它们在调用函数时的位置映射到仅位置参数。通过关键字(名称)传递位置参数是无效的。

举个例子

def foo(a, b, / , x, y):
   print("positional ", a, b)
   print("positional or keyword", x, y)

这里在上面的函数定义参数 a 和 b 是位置唯一的,而 x 或 y 可以是位置或关键字。

以下函数调用有效

foo(40, 20, 99, 39)
foo(40, 3.14, "hello", y="world")
foo(1.45, 3.14, x="hello", y="world")

但是,以下函数调用无效,这会引发异常 TypeError,因为 a、b 没有作为位置参数传递,而是作为关键字传递

foo(a=1.45, b=3.14, x=1, y=4)

TypeError: foo() 得到了一些作为关键字传递的位置参数 参数:'a,b'

Python 中的许多内置函数只接受位置参数,其中通过关键字传递参数没有意义。例如内置函数 len 只接受一个位置参数,调用 len 为 len(obj="hello world") 会影响可读性,查看 help(len)。

>>> help(len)
Help on built-in function len in module builtins:

len(obj, /)
    Return the number of items in a container.

仅位置参数使底层 c/库函数易于维护。它允许在未来更改仅位置参数的参数名称,而不会破坏使用 API 的客户端代码

最后但同样重要的是,仅位置参数允许我们使用它们的名称用于可变长度关键字参数。检查以下示例

>>> def f(a, b, /, **kwargs):
...     print(a, b, kwargs)
...
>>> f(10, 20, a=1, b=2, c=3)         # a and b are used in two ways
10 20 {'a': 1, 'b': 2, 'c': 3}

Positional-only 参数语法被正式添加到python3.8。结帐 什么是新的 python3.8 - 仅位置参数

PEP 相关:PEP 570 -- Python Positional-Only Parameters

© www.soinside.com 2019 - 2024. All rights reserved.