python自学笔记4 —— 装饰器

python自学笔记4 —— 装饰器

4.1 装饰器例程
4.1.1 单装饰
(0) 装饰函数
#这里定义一个总装饰函数,方便后续直接用于装饰被装饰函数
#注:后续函数必须加上该代码才能被正常装饰

import time     # for time.sleep

def decorate(func):
    print("正在准备装饰输入的函数")

    def drawer(*args,**kwargs):     # *args,**kwargs作用为扩大可输入参数范围
        print("开始装饰")

        #这里注意,func传入的参数应当与drawer传入参数相同,即 *args,**kwargs
        func(*args,**kwargs)    # 调用被装饰函数,位置随意,调用随意,仅为效果

        time.sleep(2)      # 仅为效果,无实际作用
        print("装饰完成")
    print("退出函数装饰")

    return drawer
(1) 被装饰函数无参数输入
@decorate# 引入调用函数
def func_1():   # 定义被装饰函数1(无参)
    print("此时装饰无参函数")

func_1()    #输出被装饰后的函数
(2) 被装饰函数有一个参数输入(字符串或者数字)
@decorate
def func_2(a):  # 定义被装饰函数2(有1参)
    print("此时装饰参数为{0}的函数".format(a))

func_2(2)   #输出被装饰后的函数
(3) 被装饰函数有两个参数输入(字符串或者数字)
@decorate# 引入调用函数
def func_3(a,b):    # 定义被装饰函数3(有2参)
    print("此时装饰参数为{0}和{1}的函数".format(a,b))

func_3(3,"glk")   #输出被装饰后的函数
(4) 被装饰函数有一个列表参数输入
list = [1,2,3,'glk']    # 定义一个列表

@decorate
def func_4(list):# 定义被装饰函数4(有列表参数)
    for i in list:
        print(i,end="")
    print("\n")     # 换行,防止与下一个被装饰函数的输出混淆

func_4(list)   #输出被装饰后的函数
(5) 被装饰函数有一个元组参数输入
tuple = (1,2,3,'好帅')  # 定义一个元组

@decorate
def func_5(tuple):
    for i in tuple:
        print(i,end="")
    print("\n")     # 换行,防止与下一个被装饰函数的输出混淆

func_5(tuple)   #输出被装饰后的函数
(6) 被装饰函数有一个字典参数输入
dict = {1 : 'glk' , 2 : '真的' , 3 : 6}   # 定义一个字典

@decorate
def func_6(dict):
    for i,j in dict.items():    # 遍历字典中的键与值
        print(i,j,"  ",end="")
    print("\n")     # 换行,防止与下一个被装饰函数的输出混淆

func_6(dict)
4.1.2 多重装饰

离 被装饰函数 最近的 装饰函数 最先装饰

def decorate1(func) :
    print("开始装饰1")
    def drawer(*args,**kwargs):
        func(*args,**kwargs)
        print("装饰1完成")
    return drawer

def decorate2(func) :
    print("开始装饰2")
    def drawer(*args,**kwargs):
        func(*args,**kwargs)
        print("装饰2完成")
    return drawer

@decorate2
@decorate1
def func_1():
    print("这里是被装饰函数")

func_1()

该代码输出为

开始装饰1
开始装饰2
这里是被装饰函数
装饰1完成
装饰2完成

输出结果分析:

  1. 首先由于离 def func_1(): 最近的是 @decorate1,故由decorate1最先装饰函数
  2. 由decorate1装饰完后,输出了“开始装饰1”,并且加载了decorate1中的drawer函数,此时drawer函数中调用的func函数是最初始的func_1(),最后传出drawer并赋值给func_1。这时,开始我们的decorate2装饰,输出了“开始装饰2”,并加载了decorate2中的drawer函数,但是,此时drawer函数中的func函数是由decorate1装饰后的func_1(),里面的内容如下
    def func_1():     #此时是被decorate1装饰后
        print("这里是被装饰函数")
        print("装饰1完成")
  1. 最后,输出decorate2中的drawer并传给func_1()。此时,当我们调用func_1()时,比被decorate1装饰后多了一句“装饰2完成”的输出。
4.1.3 带参数装饰器

三点:

  1. 带参数装饰器是三层
  2. 最外层函数用于接受参数
  3. 里面内容与普通装饰器无区别

例程如下

def outer(a):
    def decorate(func):
        print("开始装饰")
        def drawer(*args,**kwargs):
            print("所传入参数为-->{0}".format(a))
            print("正在装饰中.....")
            func(*args,**kwargs)
            print("完成装饰")
        return drawer
    return decorate

@outer("帅")
def func_1():
    print("orz  orz")

func_1()

输出如下

开始装饰
所传入参数为-->帅
正在装饰中.....
orz  orz
完成装饰
4.2 装饰器应用
# 登陆验证支付
import time

islogin = False #   初始状态为未登录
Administrator = {'glk':'123','lzt':'456','whn':'789'} #   设置一个用户系列

def login_system():
    '''登陆系统'''
    global islogin
    name = input("请输入用户名称: ")
    key = input("请输入{0}的密码: ".format(name))
    print("请稍等... ...")
    time.sleep(2)
    for i,j in Administrator.items():
        if (name == i) and (j == key):
            print("欢迎用户{0},登陆成功!".format(i))
            islogin = True  #   允许支付
            break
        else :
            print("未找到相关信息,登录失败!")
            islogin = False  #  禁止支付
            break

#定义一个装饰包,用于登录检测
def login_get(func):
    '''登陆状态检测'''
    def drawwer(*args,**kwargs):
        login_system()
        func(*args,**kwargs)
    return drawwer

@login_get
def pay_system():  #支付系统
    '''判断是否为登录状态'''
    if islogin == True: #   此时为已登录
        print("已经登录,允许支付")
        money = input("请输入支付金额: ")
        pay_ok = input("输入 'ok' 完成支付: ")
        if  pay_ok == 'ok':
            time.sleep(2)
            print("支付成功!当前支付金额为:{}元".format(money))
        else:
            print("当前未支付!")
    elif islogin == False:  #   此时为未登录
        print("暂未登录,禁止支付")

pay_system()
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值