Pae*_*els 8 python overloading python-3.5
Python 3.5+有一个重载包。使用这个包,可以重新定义方法,但是具有不同的类型提示,并且它的装饰器会找出应该调用哪个重载方法。
常见的编码模式:
class foo:
def func(param):
if instance(param, int):
pass
elif instance(param, str):
pass
elif instance(param, list):
pass
else:
raise ValueError()
Run Code Online (Sandbox Code Playgroud)
使用@overload:
class foo:
@overload
def func(param: int):
pass
@overload
def func(param: str):
pass
@overload
def func(param: list):
pass
Run Code Online (Sandbox Code Playgroud)
这是文档。
我的问题是:
从 python 3.4 开始,有一个核心 API 功能functools.singledispatch,它允许您注册重载函数。
从文档中
>>> from functools import singledispatch
>>> @singledispatch
... def fun(arg, verbose=False):
... if verbose:
... print("Let me just say,", end=" ")
... print(arg)
>>> @fun.register
... def _(arg: int, verbose=False):
... if verbose:
... print("Strength in numbers, eh?", end=" ")
... print(arg)
>>> @fun.register
... def _(arg: list, verbose=False):
... if verbose:
... print("Enumerate this:")
... for i, elem in enumerate(arg):
... print(i, elem)
Run Code Online (Sandbox Code Playgroud)
运行上述函数时(再次来自文档):
>>> fun("Hello, world.")
Hello, world.
>>> fun("test.", verbose=True)
Let me just say, test.
>>> fun(42, verbose=True)
Strength in numbers, eh? 42
>>> fun(['spam', 'spam', 'eggs', 'spam'], verbose=True)
Enumerate this:
0 spam
1 spam
2 eggs
3 spam
Run Code Online (Sandbox Code Playgroud)
注意:仅输入第一个参数!
此外,(自 python 3.8 起)还有一个等效的类方法调用functools.singledispatchmethod 的装饰器
小智 4
你必须用真实的代码自己测量它。
我快速浏览了这个库的代码,结论很简单。它使用了大量的反射(检查包)和类型比较。检查包本身主要由调试工具使用 - 它们总是会减慢你的代码速度。
只要看看这些行:
complexity = complexity_mapping[id]
if complexity & 8 and isinstance(arg, tuple):
element_type = tuple(type(el) for el in arg)
elif complexity & 4 and hasattr(arg, 'keys'):
element_type = (type(element), type(arg[element]))
else:
element_type = type(element)
Run Code Online (Sandbox Code Playgroud)
type_hints = typing.get_type_hints(func) if typing else func.__annotations__
types = tuple(normalize_type(type_hints.get(param, AnyType)) for param in parameters)
Run Code Online (Sandbox Code Playgroud)
请注意,此包如果已存在超过 7 个月且只有 70 颗星。Python 不是 Java...你真的会用这个包伤害 python 本身 :D 你最好实现一些核心 api 方法,根据类型参数将调用委托给其他方法/对象 - 就像 Python 应该做的那样。
| 归档时间: |
|
| 查看次数: |
8979 次 |
| 最近记录: |