我是一个刚开始学习python的新手,在学习python2.7,根据廖雪峰的教程在学习的,在修饰器这一段遇到了一个小问题,希望大家能够帮忙解答!谢谢!
求解释下面这段代码的运行结果?
运行的结果希望是
321 Call my_name()
JHB
但实际运行结果只有一个
JHB
def log(text):
def print_log(func):
#@functools.wraps(func)
def wrapper(*args, **kw):
print '%s Call %s():'%(text,func.__name__)
return func(*args, **kw)
return wrapper
return print_log
#@log('Hello')
def my_name():
print 'JHB'
log('321')(my_name())
Execution
log(text)
函数最终会返回一个print_log
函数,所以你的调用:log('321')(my_name())
等同于print_log(my_name())
;而
my_name()
最终只会打印出'JHB'
并返回None
,并不会返回一个func
,因此传入print_log
的参数并非一个函数,而是None
,所以print_log
函数实际上无法执行。正确的做法是,首先需要将
log('321')(my_name())
改为log('321')(my_name)
,其等同于print_log(my_name)
,该函数执行结果会返回wrapper
函数,需要注意wrapper
与wrapper()
是不同的,前者是函数的标识符,后者则是调用该函数,所以如果需要执行wrapper
,还需要增加个()
, therefore, finally change your writing to:Execution result:
Just change it to this:
Let’s look at it layer by layer. log('321') returns a function (that is, print_log). The parameter of this function is a function type, but the return value of my_name() you pass in is None type
If your purpose is to use a decorator, then you have two problems:
1. #@log('Hello') needs to remove the '#' symbol in front of it in order for the decorator to take effect on your my_name function;
2. After completing the first step, the calling method of your last line is wrong. Directly calling my_name() should be able to achieve the effect you want.
The relationship between the decorator and the decorated function and the calling sequence It’s all done by python for you