Python3的“函数注解”有哪些好的用法?
函数注解:PEP-3107
我看到了一段代码,展示了Python3中的函数注解。这个概念很简单,但我想不出为什么Python3要引入这个功能,或者有什么好的用处。也许大家能给我一些启发?
它是怎么工作的:
def foo(a: 'x', b: 5 + 6, c: list) -> max(2, 9):
... function body ...
在参数后面的冒号之后的内容就是“注解”,而在->
后面的信息是函数返回值的注解。
foo.func_annotations会返回一个字典:
{'a': 'x',
'b': 11,
'c': list,
'return': 9}
那么,拥有这个功能有什么重要意义呢?
12 个回答
49
102
函数注解的用法完全取决于你自己。
它们可以用来做文档说明:
def kinetic_energy(mass: 'in kilograms', velocity: 'in meters per second'):
...
它们也可以用来检查前置条件:
def validate(func, locals):
for var, test in func.__annotations__.items():
value = locals[var]
msg = 'Var: {0}\tValue: {1}\tTest: {2.__name__}'.format(var, value, test)
assert test(value), msg
def is_int(x):
return isinstance(x, int)
def between(lo, hi):
def _between(x):
return lo <= x <= hi
return _between
def f(x: between(3, 10), y: is_int):
validate(f, locals())
print(x, y)
>>> f(0, 31.1)
Traceback (most recent call last):
...
AssertionError: Var: y Value: 31.1 Test: is_int
另外,你可以查看 http://www.python.org/dev/peps/pep-0362/,了解如何实现类型检查。
95
我觉得这个其实很不错。
我来自学术背景,可以告诉你,注解在像Java这样的语言中,帮助智能静态分析工具变得非常重要。比如说,你可以定义一些语义,比如状态限制、哪些线程可以访问、架构限制等等。然后有很多工具可以读取这些信息,并处理它们,提供比编译器更强的保证。你甚至可以写一些东西来检查前置条件和后置条件。
我觉得在Python中尤其需要这样的东西,因为它的类型比较弱,但实际上并没有什么简单的构造可以让这个过程变得直接,并且成为官方语法的一部分。
注解的用途不仅仅是提供保证。我可以想象如何把我在Java中用的工具应用到Python上。比如,我有一个工具,可以给方法分配特殊的警告,并在你调用这些方法时提醒你要查看它们的文档(例如,想象一下你有一个方法,不应该用负值调用,但从名字上看并不直观)。有了注解,我在Python中技术上可以写出这样的东西。同样,如果有官方语法的话,还可以写一个工具,根据标签来组织一个大类中的方法。