47 单例模式 和装饰器
一.装饰 器
不改变被装饰函数原来的执行方式 给原函数增加一些额外的功能,登录验证,打印日志,测试效率等。
1.简单版装饰器
import time
#装饰器
def timer(f) : def inner(): #被装饰函数执行前 要做的事情
start_time = time.time() res = f() #被装饰的函数 #被装饰函数执行后 要做的事情 end_time = time.time() print("函数执行时间:",end_time-start_time) return res return inner @timer #相当于 func = timer(func)
#被装饰函数
def func(x,y):
print(x+y)
return x+y
func()
2.带参数的装饰器
带参数装饰器一 :控制装饰器的关和开
# 带参数的装饰器 可以同时控制装饰器的启用和关闭 import time def timmer(flag): def wrapper(f): def inner(*args, **kwargs): if flag: start_time = time.time() ret = f(*args, **kwargs) end_time = time.time() print('执行时间%s' % (end_time-start_time)) return ret else: ret = f(*args, **kwargs) return ret return inner return wrapper flag1 = False @timmer(flag1) # 第一步,将@ 与后面 分开,只是单纯的执行timmer(flag1)函数 第二步 将@ 与 wrapper相结合,形成装饰器 def func1(): time.sleep(0.3) print('in func1') @timmer(flag1) def func2(): time.sleep(0.3) print('in func2') @timmer(flag1) def func3(): time.sleep(0.3) print('in func3') func1() func2() func3()
带参数装饰器二 :
# 做一个带参数的装饰器: # 访问JD JD_shop 输入京东的账号密码 # 访问taobao tianmao_shop() 输入支付宝的账号密码 status = { "username":None, "京东":False, "淘宝":False } def login(flag): def wapper(f): def inner(*args,**kwargs): if status[flag]: res = f(*args,**kwargs) return res else: print("-----登录页面-------") username = input("请输入用户名:").strip() password = input("请输入密码:").strip() with open(flag,"r",encoding="utf-8") as f1: for line in f1: user,pwd = line.strip().split("|") if user.strip() == username and password == pwd.strip(): status [flag] = True print("登录成功!") res = f(*args, **kwargs) return res else: print("登录失败!") return inner return wapper @login('京东') def JD(): print("-----欢迎进入京东首页!------") @login('京东') def JD_shop(): print("-----欢迎进入京东商店!------") @login('淘宝') def taobao(): print("-----欢迎进入淘宝首页!------") @login('淘宝') def tianmao_shop(): print("-----欢迎进入天猫超市!------") JD() JD_shop() taobao() tianmao_shop()
3. 多个装饰器,装饰同一个函数
#多个装饰器 装饰一个函数 def wrapper1(func): # func == f 函数名 def inner1(): print('wrapper1 ,before func') # 2 func() print('wrapper1 ,after func') # 4 return inner1 def wrapper2(func): # func == inner1 def inner2(): print('wrapper2 ,before func') # 1 func() print('wrapper2 ,after func') # 5 return inner2 # 就近原则 @wrapper2 # f = wrapper2(f) 里面f == inner1 外面的f == inner2 @wrapper1 # f = wrapper1(f) 里面的f == 函数名f 外面的f == inner1 def f(): print('in f') # 3 f() # inner2()
二. 单例模式
#单例模式 :只能创建同一个实例对象 class A: def __new__(cls, *args, **kwargs): print(111) obj = object.__new__(cls) return obj def __init__(self): print(222) obj1 = A() class A: __instance = None def __new__(cls, *args, **kwargs): if A.__instance is None: obj = object.__new__(cls) A.__instance = obj return A.__instance obj1 = A() obj2 = A() obj3 = A() obj4 = A() print(obj1) print(obj2) print(obj3) print(obj4)
有疑问可以加wx:18179641802,进行探讨