• python中的闭包和装饰器的使用


    函数参数

    在python中,函数可以当作参数使用

    def func01():
        print("func01 is show ......")
    
    
    # func01()
    # 函数名存放的是函数所在空间的地址
    # print(func01)
    # 函数名也可以像普通变量一样赋值
    # func02 = func01
    # func02()
    
    def foo(func):
        func()
    
    
    foo(func01)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16

    闭包的构成条件

    1.在函数嵌套(函数里面再定义函数)的前提下
    2.内部函数使用了外部函数的变量(还包括外部函数的参数)
    3.外部函数返回了内部函数

    # 闭包的构成条件:
    # 1在函数嵌套(函数里面再定义函数)的前提下
    
    def func_out(num1):
        def func_inner(num2):
            # 2内部函数使用了外部函数的变量(还包括外部函数的参数)
            num = num1 + num2
            print("num的值为", num2)
    
        # 3外部函数返回了内部函数
        return func_inner
    
    
    # 创建闭包实例
    f = func_out(10)
    # 执行闭包
    f(1)
    f(2)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18

    基础的闭包的使用

    # 外部函数
    def config_name(name):
        # 内部函数
        def say_info(info):
            print(name + ":" + info)
    
        return say_info
    
    
    tom = config_name("tom")
    tom("你好")
    tom("你在吗")
    
    jerry = config_name("jerry")
    jerry("你好")
    jerry("我在呢")
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16

    nonloal关键字的使用

    1.非局部声明变量指代的已有标识符是最近外面函数的已声明变量,但是不包括全局变量。这个是很重要的,因为绑定的默认行为是首先搜索本地命名空间。nonlocal声明的变量只对局部起作用,离开封装函数,那么该变量就无效。
    2.非局部声明不像全局声明,我们必须在封装函数前面事先声明该变量
    3.非局部声明不能与局部范围的声明冲突

    # 外部函数
    def func_out(num1):
        # 内部函数
        # aaa = 10
    
        def func_inner(num2):
            nonlocal num1
            num1 = num2 + 10
    
        print(num1)
        func_inner(10)
        print(num1)
    
        return func_inner
    
    
    # num1 = 10
    # f = func_out(10)
    # 调用闭包 = 内部函数 num2 = 10
    # f(10)
    
    func_out(10)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22

    基础代码实现(装饰器

    # 1.定义一个装饰器(装饰器的本质是闭包)
    def check(fn):
        def inner():
            print("登录验证")
            fn()
    
        return inner
    
    
    # 需要被装饰的函数
    def comment():
        print("发表评论")
    
    
    # 2使用装饰器装饰函数(增加一个登录功能)
    comment = check(comment)
    comment()
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18

    装饰器的基本使用

    # 1定义一个装饰器(装饰器的本质是闭包)
    def check(fn):
        def inner():
            print("请先登陆")
            fn()
    
        return inner
    
    
    # 2使用装饰器装饰函数(增加一个登陆功能)
    # 解释器遇到@check 会立即执行 comment = check(comment)
    
    @check
    def comment():
        print("发表评论")
    
    
    comment()
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18

    装饰器的使用

    import time
    
    
    # 1 定义装饰器
    def get_time(fn):
        def inner():
            start = time.time()
            fn()
            end = time.time()
    
            print("时间:", end - start)
    
        return inner
    
    
    # 2 装饰函数
    # 要被装饰的函数
    @get_time
    def func():
        for i in range(100000):
            print(i)
    
    
    func()
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25

    有参数的装饰器的使用

    # 定义装饰器
    def logging(fn):  # fn = sum_num
        def inner(a, b):
            fn(a, b)
    
        return inner  # sum_num = inner
    
    
    # 使用装饰器装饰函数
    @logging
    def sum_num(a, b):
        result = a + b
        print(result)
    
    
    sum_num(1, 2)
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17

    带有返回值的装饰器

    # 定义装饰器
    def logging(fn):  # fn = sum_num
        def inner(a, b):
            result = fn(a, b)
            return result
    
        return inner  # sum_num = inner
    
    # 使用装饰器装饰函数
    @logging
    def sum_num(a, b):
        result = a + b
        return result
    
    
    result = sum_num(1, 2)
    print(result)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17

    带有不定长参数的装饰器

    # 定义装饰器
    def logging(fn):  # fn = sum_num
        def inner(*args, **kwargs):
            fn(*args, **kwargs)
    
        return inner  # sum_num = inner
    
    # 使用装饰器装饰函数
    @logging
    def sum_num(*args, **kwargs):
        print(args, kwargs)
    
    
    sum_num(1, 2, 3, age="18")
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14

    带有参数的装饰器的使用

    # 装饰器
    def logging(flag):  # flag = "+"
    
        # 外部函数
        def decorator(fn):
            # 内部函数
            def inner(num1, num2):
                # 判断流程
                if flag == "+":
                    print("--正在努力加法计算--")
                elif flag == "-":
                    print("--正在努力减法计算--")
                result = fn(num1, num2)
                return result
    
            return inner
    
        # 返回装饰器
        return decorator
    
    
    # 被带有参数的装饰器装饰的函数
    @logging('+')  # 1 logging("+") 2 @decorator起到装饰器的功能了
    def add(a, b):
        result = a + b
        return result
    
    
    # 执行函数
    result = add(1, 3)
    print(result)
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32

    类装饰器的使用

    # 定义类装饰器
    class Check(object):
        def __init__(self, fn):
            self.__fn = fn
    
        def __call__(self, *args, **kwargs):
            print("登录")
            self.__fn()
    
    
    @Check
    def comment():
        print("发表评论")
    
    
    comment()
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
  • 相关阅读:
    QT中窗口自绘制效果展示
    上海亚商投顾:沪指缩量跌0.43%
    如何通过链路追踪进行定时任务诊断
    Python、QT的人脸识别项目
    选择排序算法(思路分析) [数据结构][Java]
    重磅官宣|数说故事战略并购考古加,打造多样化客户服务生态
    关于python中自带的类似postman的工具
    YbtOJ「动态规划」第4章 树形DP
    基于半局部结构的异常连边识别算法
    可视化查询(sp_helptext)——快速查询包含指定字符串的存储过程(附源码)
  • 原文地址:https://blog.csdn.net/qq_45724328/article/details/127902539