【笔记2】python中@的用法

python中@的用法

@是一个装饰器,针对函数,起调用传参的作用。
有修饰和被修饰的区别,‘@function’作为一个装饰器,用来修饰紧跟着的函数(可以是另一个装饰器,也可以是函数定义)。

代码1:修饰函数

def funA(desA):
    print("It's funA")
    print('---')
    print(desA)
    desA()
    print('---')

@funA
def funC():
    print("It's funC")

结果1

It's funA
---------
<function funC at 0x7f9667abadc0>
It's funC
---------

分析1

@funA修饰函数定义funC,传址funCfunA,为了更直观地看参数传递,打印desA,其传的是funC的地址。

执行的时候由上而下,先定义funA,然后运行funA(funC),输出‘It’s funA’。
执行desA()即调用funC,执行funC()。

值得注意的是

直接修饰和执行funA(funC)的区别

代码1和直接执行funA(funC)的结果有些出入。

> 代码1
> 
	It's funA
	---------
	<function funC at 0x7f9667abadc0>
	It's funC
	---------



> funA(funC)
> 
	It's funA
	---------
	None
	Traceback (most recent call last):
	  File "main.py", line 16, in <module>
	    funA(funC)
	  File "main.py", line 8, in funA
	    desA()
	TypeError: 'NoneType' object is not callable

  • 为什么print(desA)None
  • 为什么desA()报错TypeError: 'NoneType' object is not callable
    同一个原因:修饰器函数funA里没有定义返回值。修饰器@funA接收函数funC作为参数,在修饰器函数funA中可以修改参数函数funC,当我们调用被修饰的函数funC时,实际上是在执行被修改过的修饰器函数,但在funA中我们没有返回可调用的函数,默认返回的是None,所以会出现这两个问题,在funA中加上返回值(被修饰后的参数)就可以解决。
def funA(desA):
    print("It's funA")
    print('---')
    print(desA)
    desA()
    print('---')
    
    return desA  # <-- missing return statement before

@funA
def funC():
    print("It's funC")
funA(funC)funA(funC())差别

funA(funC)funA(funC())是不同的,之前一个笔误将这里的函数调用写成后者。如果我们要执行funA(funC()),也会报错。

> funA(funC)
> 
	It's funA
	---------
	<function funC at 0x7fe2a4f04dc0>
	It's funC
	---------



> funA(funC())
> 
	It's funC
	It's funA
	---------
	None
	Traceback (most recent call last):
	  File "main.py", line 17, in <module>
	    funA(funC())
	  File "main.py", line 8, in funA
	    desA()
	TypeError: 'NoneType' object is not callable
  • 为什么多打印了It's funC?
  • 为什么print(desA)None
  • 为什么desA()报错TypeError: 'NoneType' object is not callable
    这个执行顺序由内向外,先调用funC(),打印了这一句,然后将调用结果返回传给funA,在这里传的并不是函数地址,而是函数结果,是一个None,如果想要不报错,需要在funC返回一个可调用的函数,这与代码1完全不一样。

代码2:修饰装饰器

def funA(desA):
    print("It's funA")
    return desA

def funB(desB):
    print("It's funB")
    return desB

@funB
@funA
def funC():
    print("It's funC")

结果2

It's funA
It's funB

分析2

@funB 修饰装饰器@funA,@funA 修饰函数定义def funC(),将funC传给funA,再将funA(funC)传给funB。
执行的时候由上而下,先定义funA、funB,然后运行funB(funA(funC))。
此时desA=funC(),然后funA()输出‘It’s funA’;desB=funA(funC),然后funB()输出‘It’s funB’。


  • 13
    点赞
  • 36
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值