重新认识Python装饰器

前言

面试被问到解释一下装饰器的问题时, 我都会回答到, “装饰器就是一个输入函数返回函数的函数(可调用对象)”. 当然这也是大家经常看到的解释. 直到遇到一个面试官接着问了一句, “装饰器一定要返回函数吗?”, 本文也就是从这个问题开始的.

装饰器是什么

我们可以查阅官方文档装饰器 | 函数定义 | 类定义, 可以发现装饰器大概也就是我前言里的一句话, “装饰器就是一个输入函数返回函数的函数”, 类也可以用装饰器, 无非就是换个词, “一个输入类返回类的函数”.

我在文档中注意到这样一个解释

装饰器语法只是一种语法糖,以下两个函数定义在语义上完全等价:

def f(arg):
       ...
f = staticmethod(f)

@staticmethod
def f(arg):
       ...

这也许就是装饰器在语义上的一个本质, 仅仅是把函数f当作参数给函数d, 然后将函数d的返回值重新绑定到名字f上. 所以我猜测装饰器函数可以返回除了函数和类之外的其他对象, 赶紧试试下面的代码.

def d(func):
    return 1

@d
def foo():
	pass

print(foo, type(foo))
# 1 <class 'int'>

结果不出所料, 装饰器可以返回其他任何类型的对象, 只要你想.

但正如我听到这个问题时, 说出来的第一句话一样, “不返回函数的装饰器还叫装饰器吗?”.

重新认识装饰器

从这里我觉得装饰器这个概念需要从两个方面去讨论

应用

应用上的装饰器就是一种接受一个函数, 返回一个函数的函数(类装饰器自行带入), 广泛应用与面向切面编程的场景, 例如日志输出 | 权限认证 | 错误处理等.

语法与语义

语法上, 装饰器就是一个语法糖, 装饰器函数可以不返回函数, 可以返回任何东西, 最后会重新绑定到变量名上, 当然这个装饰器函数至少要接受一个参数, 不然会报错.

后记

后来我才意识到, 面试官只是想引导告诉我还有类装饰器而已, 并没有到探讨语法与应用一致性的问题, 后面我从这个问题入手重新梳理了一下装饰器, 有了今天这篇文章.

网上没有找到相关的讨论, 这是我自己通过观察代码运行结果和思考的结果, 分成应用和语法两方面也是我主观上分的, 或许有问题, 所以

如有问题, 欢迎交流!

参与评论 您还未登录,请先 登录 后发表或查看评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
©️2022 CSDN 皮肤主题:大白 设计师:CSDN官方博客 返回首页

打赏作者

i止于至善

你的鼓励将是我创作的最大动力

¥2 ¥4 ¥6 ¥10 ¥20
输入1-500的整数
余额支付 (余额:-- )
扫码支付
扫码支付:¥2
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值