装饰器

Posted shaozheng

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了装饰器相关的知识,希望对你有一定的参考价值。

闭包:

什么是闭包:

函数内部函数对外部作用域而非全局作用域的引用

应用:延迟计算,爬虫领域

装饰器:

无参装饰器

什么是装饰器:

为被装饰器对象添加额外功能

注意:

装饰器本省其hi书可以任意调用的对象

被装饰的对象也可以是任意可调用的对象

原则:

1.不修改被装饰对象的源代码

2.不修改被装饰对象的调用方式

3.用来装饰函数的,它本质是函数

原理:遵循原则的前提下为被装饰对象添加新功能

如何用:

import time


def index():
    print('welcome to index')
    time.sleep(1)

    return 123


def time_count(func):
    # func = 最原始的index
    def wrapper():
        start = time.time()
        res = func()
        end = time.time()
        print(f"func time is start-end")

        return res
    return wrapper


index = time_count(index)
res = index()
print(res)

装饰器语法糖:

--在被装饰函数的正上方,并且是单独一行写上 -”@装饰器名“

import time


def time_count(func):
    # func = 最原始的index
    def wrapper(*args, **kwargs):
        start = time.time()
        res = func(*args, **kwargs)
        end = time.time()
        print(f"func time is start-end")

        return res
    return wrapper


@time_count  # home = time_count(home)
def home(name):
    print(f"welcome name to home page")
    time.sleep(1)

    return name


@time_count  # index = time_count(index)
def index():
    print('welcome to index')
    time.sleep(1)

    return 123
res = home('egon')
print(f"res: res"")

装饰器模板:

def deco(func):
    def wrapper(*args,**kwargs):
        """加功能"""
        res = func(*args,**kwargs)
        return res
    return wrapper

有参函数:

import time
current_user = 'username':None
def login(func):
    def wrapper(*args,**kwargs):
        if current_user['username']:
            res = func(*args,**kwargs)
            return res

        user = input('username: ').strip()
        pwd = input('password: ').strip()

        engine = 'file'
        if engine =='file':
            print('base of file')
            if user == 'nick' and pwd == '123':
                print('login successful')
                current_user['user'] = user
                res = func(*args,**kwargs)
                return res
            else:
                print('user or password error')
        elif engine =='mysql':
            print('base of mysql')
        elif engine == 'mongodb':
            print('base of mongodb')
        else:
            print('default')

    return wrapper()

# @login
# def home(name):
#     print(f'welcome name to home page')
#     time.sleep(1)

@login --@login #  === index = login_deco(index)
def index():
    print('welcome to index')
    time.sleep(1)


res = index()
print(res)

三层闭包:

两层的装饰器,参数必须得固定位func,但是三层的装饰器解除了这个限制,多个参数的只需要在三层装饰器中多加入几个参数即可。

import time

current_uesr = 'username': None


def auth(engine='file'):

    def login(func):
        # func = 最原始的index
        def wrapper(*args, **kwargs):

            if current_user['username']:
                res = func(*args, **kwargs)

                return res

            user = input('username: ').strip()
            pwd = input('password: ').strip()

            if engine == 'file':
                print('base of file')
                if user == 'nick' and pwd == '123':
                    print('login successful')
                    current_uesr['usre'] = user
                    res = func(*args, **kwargs)

                    return res
                else:
                    print('user or password error')
            elif engine == 'mysql':
                print('base of mysql, please base of file')
            elif engine == 'mongodb':
                print('base of mongodb, please base of file')
            else:
                print('please base of file')

        return wrapper

    return login


@auth(engine='mysql')
def home(name):
    print(f"welcome name to home page")
    time.sleep(1)


@auth(engine='file')
def index():
    print('welcome to index')
    time.sleep(1)


res = index()

以上是关于装饰器的主要内容,如果未能解决你的问题,请参考以下文章

python 装饰器:装饰器实例类装饰器(装饰函数)

装饰器、装饰器类与类装饰器(三)

Python进阶装饰器(Decorator)

python 装饰器:装饰器实例内置装饰器

python 装饰器:装饰器实例内置装饰器

TS之装饰器