python装饰器作用
python装饰器就是用于拓展原来函数功能的一种函数,这个函数的特殊之处在于它的返回值也是一个函数,使用python装饰器的好处就是在不用更改原函数的代码前提下给函数增加新的功能
完整的装饰器:
import time
def timmer(func):
def deco():
start_time=time.time()
func()
stop_time=time.time()
print("in the func run is %s" % (stop_time-start_time))
return deco
@timmer #test1=timmer(test1)
def test1():
time.sleep(3)
print("in the test1")
@timmer #=test2=timmer(test2)
def test2():
time.sleep(3)
print("in the test2")
test1()
test2()
C:\Python34\python.exe C:/Users/Administrator/PycharmProjects/untitled25/lianxi.py
in the test1
in the func run is 3.0001721382141113
in the test2
in the func run is 3.00017094612121
自己编写的完整的装饰器
# -*- coding:UTF-8 -*-
import time
def timmer(func):
def deco():
func()
print("welcome to beijing")
return deco
@timmer #test1=timmer(test1)
def test1():
time.sleep(3)
print("in the test1")
@timmer #=test2=timmer(test2)
def test2():
time.sleep(3)
print("in the test2")
test1()
test2()
ssh://root@192.168.0.75:22/usr/bin/python -u /app/py_code/test3.py
in the test1
welcome to beijing
in the test2
welcome to beijing
传参数
import time
def timmer(func):
def deco(name):
start_time=time.time()
func(name)
stop_time=time.time()
print("in the func run is %s" % (stop_time-start_time))
return deco
#@timmer #=test1=timmer(test1)
def test1():
time.sleep(3)
#print("in the test1")
@timmer #=test2=timmer(test2)
def test2(name):
time.sleep(3)
print("in the test2",name)
test1()
test2("bob")
C:\Python34\python.exe C:/Users/Administrator/PycharmProjects/untitled25/lianxi.py
in the test2 bob
in the func run is 3.000170946121216
import time
def timmer(func):
def deco(arg1,arg2):
start_time=time.time()
func(arg1,arg2)
stop_time=time.time()
print("in the func run is %s" % (stop_time-start_time))
return deco
#@timmer #=test1=timmer(test1)
def test1():
time.sleep(3)
#print("in the test1")
@timmer #=test2=timmer(test2)
def test2(name,age):
time.sleep(3)
print("in the test2",name,age)
test1()
test2("bob",25)
C:\Python34\python.exe C:/Users/Administrator/PycharmProjects/untitled25/lianxi.py
in the test2 bob 25
in the func run is 3.000170946121216
通用型传递参数的装饰器
import time
def timmer(func):
def deco(*args,**kwargs):
start_time=time.time()
func(*args,**kwargs)
stop_time=time.time()
print("in the func run is %s" % (stop_time-start_time))
return deco
#@timmer #=test1=timmer(test1)
def test1():
time.sleep(3)
#print("in the test1")
@timmer #=test2=timmer(test2)
def test2(name,age,high):
time.sleep(3)
print("in the test2",name,age,high)
test1()
test2("bob",25,170)
C:\Python34\python.exe C:/Users/Administrator/PycharmProjects/untitled25/lianxi.py
in the test2 bob 25 170
in the func run is 3.0001721382141113
https://www.cnblogs.com/cicaday/p/python-decorator.html
基于类实现的装饰器:
装饰器要求接受一个callable对象,并返回一个callable对象(不太严谨,详见后文)。那么用类来实现也是也可以的。我们可以让类的构造函数__init__()接受一个函数,然后重载__call__()并返回一个函数,也可以达到装饰器函数的效果。
class logging(object):
def __init__(self, func):
self.func = func
def __call__(self, *args, **kwargs):
print ("[DEBUG]: enter function {func}()".format(
func=self.func.__name__))
return self.func(*args, **kwargs)
@logging
def say(something):
print ("say {}!".format(something))
say('hello')
E:\python\python.exe E:/django工程/第20章/app01/cehi3.py
[DEBUG]: enter function say()
say hello!
自己改编的基于类实现的装饰器
# -*- coding:UTF-8 -*-
class logging(object):
def __init__(self, func):
self.func = func
def __call__(self, *args, **kwargs):
print ("[DEBUG]: enter function")
return self.func(*args, **kwargs)
@logging
def say(something):
print ("say",something)
say('hello')
ssh://root@192.168.0.75:22/usr/bin/python -u /app/py_code/test3.py
[DEBUG]: enter function
say hello
带参数的类装饰器
如果需要通过类形式实现带参数的装饰器,那么会比前面的例子稍微复杂一点。那么在构造函数里接受的就不是一个函数,而是传入的参数。通过类把这些参数保存起来。然后在重载__call__方法是就需要接受一个函数并返回一个函数。
class logging(object):
def __init__(self, level='INFO'):
self.level = level
def __call__(self, func): # 接受函数
def wrapper(*args, **kwargs):
print "[{level}]: enter function {func}()".format(
level=self.level,
func=func.__name__)
func(*args, **kwargs)
return wrapper #返回函数
@logging(level='INFO')
def say(something):
print "say {}!".format(something)
E:\python\python.exe E:/django工程/第20章/app01/cehi3.py
[INFO]: enter function say()
say hello!
带参数的类装饰器--自己改编的
# -*- coding:UTF-8 -*-
class logging(object):
def __init__(self, level='INFO'):
self.level = level
def __call__(self, func): # 接受函数
def wrapper(*args, **kwargs):
print ("[{level}]: enter function")
func(*args, **kwargs)
return wrapper #返回函数
@logging(level='INFO')
def say(something):
print ("say",something)
say('hello')
内置装饰器
python中@property装饰器的用法
参照:https://blog.csdn.net/wzqnls/article/details/53587049
不使用@property实现类
class Boy(object):
def __init__(self, name):
self.name = name
def get_name(self):
return self.name
def set_name(self, new_name):
self.name = new_name
def del_name(self):
del self.name
boy = Boy('Tom')
print(boy.get_name())
E:\python\python.exe E:/django工程/第20章/app01/cehi3.py
Tom
Alice
使用@property实现上述类
class Boy(object):
def __init__(self, name):
self._name = name
@property
def name(self):
return self._name
# 下面这个装饰器是由上面的@property衍生出来的装饰器
@name.setter
def name(self,new_name):
self._name = new_name
@name.deleter
def name(self):
del self._name
boy = Boy('Tom')
boy.name = 'white dog'
print(boy.name)
del boy.name
实例二:
class Animal(object):
def __init__(self, name, age):
self._name = name
self._age = age
self._color = 'Black'
@property
def name(self):
return self._name
@name.setter
def name(self, value):
self._name = value
@property
def age(self):
return self._age
@age.setter
def age(self, value):
if value > 0 and value < 100:
self._age = value
else:
self._age = 0
# print 'invalid age value.'
@property
def color(self):
return self._color
@color.setter
def color(self, style):
self._color = style
a = Animal('black dog', 3)
a.name = 'white dog'
a.age = 300
print ('Name:', a.name)
print ('Age:', a.age)