在Python函数定义中是什么意思?

我最近注意到Python 3.3语法规范时有一些有趣的地方:

funcdef: 'def' NAME parameters ['->' test] ':' suite 

Python 2中没有可选的“箭头”块,我在Python 3中找不到任何有关它的含义的信息。事实certificate这是正确的Python,它被解释器接受:

 def f(x) -> 123: return x 

我认为这可能是某种先决条件语法,但是:

  • 我不能在这里testingx ,在这里还是没有定义,
  • 无论我放在箭头后面(例如2 < 1 ),它都不会影响function行为。

任何人都可以习惯这个语法解释吗?

这是一个function注释 。

更详细地说,Python 2.x具有文档string,它允许您将元数据string附加到各种types的对象。 这非常方便,所以Python 3通过允许您将元数据附加到描述其参数和返回值的函数来扩展该function。

没有先入为主的用例,但是PEP提出了几个。 一个非常方便的是允许你用他们期望的types注释参数; 那么编写一个装饰器来validation注解或者将参数强制转换为正确的types将很容易。 另一个是允许参数特定的文档,而不是编码到文档string。

这些是PEP 3107中涵盖的function注释。 具体来说, ->标记返回函数注释。

例子:

 >>> def kinetic_energy(m:'in KG', v:'in M/S')->'Joules': ... return 1/2*m*v**2 ... >>> kinetic_energy.__annotations__ {'return': 'Joules', 'v': 'in M/S', 'm': 'in KG'} 

注释是词典,所以你可以这样做:

 >>> '{:,} {}'.format(kinetic_energy(20,3000), kinetic_energy.__annotations__['return']) '90,000,000.0 Joules' 

你也可以有一个Python数据结构,而不仅仅是一个string:

 >>> rd={'type':float,'units':'Joules','docstring':'Given mass and velocity returns kinetic energy in Joules'} >>> def f()->rd: ... pass >>> f.__annotations__['return']['type'] <class 'float'> >>> f.__annotations__['return']['units'] 'Joules' >>> f.__annotations__['return']['docstring'] 'Given mass and velocity returns kinetic energy in Joules' 

或者,您可以使用函数属性来validation调用的值:

 def validate(func, locals): for var, test in func.__annotations__.items(): value = locals[var] try: pr=test.__name__+': '+test.__docstring__ except AttributeError: pr=test.__name__ msg = '{}=={}; Test: {}'.format(var, value, pr) assert test(value), msg def between(lo, hi): def _between(x): return lo <= x <= hi _between.__docstring__='must be between {} and {}'.format(lo,hi) return _between def f(x: between(3,10), y:lambda _y: isinstance(_y,int)): validate(f, locals()) print(x,y) 

打印

 >>> f(2,2) AssertionError: x==2; Test: _between: must be between 3 and 10 >>> f(3,2.1) AssertionError: y==2.1; Test: <lambda> 

正如其他答案所述, ->符号被用作function注释的一部分。 在Python >= 3.5更新版本中,它具有定义的含义。

PEP 3107 – 函数注释描述了规范,定义了语法变化,存储了它们的func.__annotations__ ,而且它的用例仍然是开放的。

但在Python 3.5 , PEP 484-Type Hints附加了一个单一的含义: ->用于指示函数返回的types。 它也似乎像将在以后的版本中执行,如在注释的现有使用情况中所述 :

最快的可以想象的scheme将在3.6中引入对非types提示注释的静态弃用,在3.7中完全弃用,并且将types提示声明为Python 3.8中唯一允许使用的注释。

(强调我的)

据我所知,这实际上还没有实施,所以可能会碰到未来的版本。

据此,你提供的例子:

 def f(x) -> 123: return x 

将来会被禁止(当前版本会令人困惑),则需要将其更改为:

 def f(x) -> int: return x 

因为它有效地描述函数f返回一个inttypes的对象。

Python本身没有以任何方式使用注释,它几乎填充并忽略它们。 第三方库需要与他们合作。

Interesting Posts