zoukankan      html  css  js  c++  java
  • python装饰器

    装饰器

    装饰函数,扩展功能

    装饰器作用

    1.不修改函数的调用方式

    2.给原来的函数添加新的功能

    开发封闭原则

    1.开发:对扩展开发

    2.封闭:对修改封闭

    示例

    例1:计算代码运行时间

    import time
    def func():
        start_time = time.time()
        print('from the func')
        time.sleep(1)
        end_time = time.time()
        print(end_time - start_time)
    func()
    
    # 执行结果
    from the func
    1.0009381771087646

    例2:计算函数运行时间

    def timmer(f):
        start_time = time.time()
        f()
        end_time = time.time()
        print(end_time-start_time)
    
    def func():
        print('from the func')
        time.sleep(1)
    func()
    timmer(func)  # 传入函数名就得到该函数的执行时间

     语法糖

    import time
    def timmer(func):
        def inner():
            start_time = time.time()
            func()
            end_time = time.time()
            print(end_time-start_time)
        return inner
    
    @timmer  # 相当于func = timmer(func)
    def func():  # 被装饰的函数
        print('from the func')
        time.sleep(1)
    func()

     例3:带参数的装饰器

      1.在装饰器外面再加一层函数

      2.利用局部调用全局变量

      3.不需要装饰器时需改标识

    import time
    # flag = True
    flag = False
    def timmer_out(flag):
        def timmer(func):
            def inner(*args,**kwargs):
                if flag:
                    start_time = time.time()
                    ret = func(*args,**kwargs)
                    end_time = time.time()
                    print(end_time-start_time)
                    return ret
                else:
                    ret = func(*args, **kwargs)
                    return ret
            return inner
        return timmer
    
    # timmer = timmer_out(flag)
    # @timmer
    @timmer_out(flag)  
    def func1():
        time.sleep(0.5)
        print('from func1')
    
    @timmer_out(flag)
    def func2():
        time.sleep(0.5)
        print('from func2')
    
    func1()
    func2()

    例4:调用内置双下划线

    from functools import wraps
    def wrapper(func):
        @wraps(func)
        def inner(*args,**kwargs):
            print('在被装饰函数执行前动作')
            ret = func(*args,**kwargs)
            print('在被装饰函数执行后动作')
            return ret
        return inner
    
    @wrapper  # holiday = wrapper()
    def holiday(day):
        '''
        这是一个放假通知
        :param day: 
        :return: 
        '''
        print('放假时间%s'%day)
        return 'happy'
    
    ret = holiday(3)
    print(ret)
    print(holiday.__name__)  # 查看函数名
    print(holiday.__doc__)  # 查看注释

     类中方法

    1.普通方法,没有任何参数,只能类来调用。

    2.绑定方法:1)绑定到对象;2)绑定到类

    3.静态方法:无论对象还是类都可以调用

    class MyClass():
        # 普通方法
        def methoda():
            print("普通方法")
        # 绑定方法(绑定对象)
        def methodb(self):
            print("绑定到对象方法")
        # 绑定方法(绑定到类)
        @classmethod
        def methodc(cls):
            print(cls)
            print("绑定到类方法")
        # 静态方法
        @staticmethod
        def methodd(arg):
            print("静态方法")
    
    # 实例化
    obj = MyClass()
    MyClass.methoda() # 普通方法
    obj.methodb() # 绑定方法(绑定对象)
    MyClass.methodb(111) # 绑定方法(绑定对象) 手动传参
    MyClass.methodc() # 绑定方法(绑定到类)
    obj.methodc() # 绑定方法(绑定到类)
    obj.methodd(111) # 静态方法
    MyClass.methodd(111) # 静态方法
    
    # 默认在类外,动态添加动态方法
    obj.func = lambda : print(123)
    obj.func()
    
    """
    执行结果:
    ----- 普通方法 绑定到对象方法 绑定到对象方法 <class '__main__.MyClass'> 绑定到类方法 <class '__main__.MyClass'> 绑定到类方法 静态方法 静态方法 123
    """

     property装饰器

    可以把成员方法变成属性,控制成员的获取设置删除。

      @自定义.setter 设置

      @自定义.deleter 删除

    写法一:

    class MyClass():
        def __init__(self,name):
            self.name = name
        @property
        def username(self):
            return self.name
        @username.setter
        def username(self,val):
            self.name = val
        @username.deleter
        def username(self):
            del self.name
    
    # 把username方法变成属性
    obj = MyClass("test")
    print(obj.username)
    
    # 设置username
    obj.username = "Python"
    print(obj.username)
    
    # 删除username
    del obj.username

    写法二:

    class MyClass():
        def __init__(self,name):
            self.name = name
        @property
        def username(self):
            return self.name
        @username.setter
        def username(self,val):
            self.name = val
        @username.deleter
        def username(self):
            del self.name
    
    # 把username方法变成属性
    obj = MyClass("test")
    print(obj.username)
    
    # 设置username
    obj.username = "Python"
    print(obj.username)
    
    # 删除username
    del obj.username
  • 相关阅读:
    Qt 查询字符串数据
    #include <stdint.h>
    滤波器设计-巴特沃尔斯低通滤波设计 转
    小波学习之二(单层一维离散小波变换DWT的Mallat算法C++实现优化)--转载
    机器学习之Bagging与随机森林笔记
    机器学习之决策树笔记
    机器学习之softmax回归笔记
    机器学习之逻辑回归(Logistic)笔记
    机器学习之模型拟合效果的判断笔记
    机器学习最小二乘法笔记
  • 原文地址:https://www.cnblogs.com/wangzihong/p/11332156.html
Copyright © 2011-2022 走看看