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

    装饰器

     

    1、定义:假设我们要增强一个函数的功能,比如,在函数调用前后自动打印日志,但又不希望改变这个函数的源代码,这种在代码运行期间动态增加功能且又不改变源代码的方式,成为装饰器(Decorator)。本质上,decorator就是一个返回函数的高阶函数

    2.实例

     如上图中的原函数为index(),我们通过装饰器为其增加了一个计算运行时间的功能,但是没有改变源代码,这就是为其增加了一个装饰器,装饰器的功能就是计时。

     关键点:@的语法,@timmer等同于进行了如下操作:index=timmer(index),函数名+()就是调用函数,一定要记住!!好多地方想不通原因就是在这里!

     思想就是把部内函数func()换成被装饰函数index()然后再运行闭包函数就好了(可能说的有点简单)

    3、给认证装饰器增加一个登陆后再次调用是免认证的功能(字典,只在内存中能行)

    import time
    
    current_login = {'name': None, 'login': False}  # 建立一个字典,字典存储登录状态
    
    
    def timmer(func):
        def wrapper():
            start_time = time.time()
            func()
            stop_time = time.time()
            print('run time is %s' % (stop_time - start_time))
    
        return wrapper
    
    
    def auth2(auth_type='file'):
        def auth(func):
            def wrapper(*args, **kwargs):
                if current_login['name'] and current_login['login']:  # 判断状态是否被激活,若激活直接执行函数结束
                    res = func(*args, **kwargs)
                    return res
                if auth_type == 'file':
                    name = input('username:')
                    password = input('password:')
                    if name == 'zhejiangF4' and password == 'sb945':
                        print('auth successful')
                        res = func(*args, **kwargs)
                        current_login['name'] = name  # 存储登录状态
                        current_login['login'] = True
                        return res
                    else:
                        print('auth error')
                elif auth_type == "sql":
                    print("haibuhui")
    
            return wrapper
    
        return auth
    
    
    @timmer
    @auth2(auth_type="file")
    def index():
        print('welcome to index page')
    
    
    @auth2("file")
    def home():
        print("welcome to home page")
    
    
    index()
    home()  # 第一次执行index()函数是需要登录认证,但第二次执行home时就不需要再认证了
    

      

     4.帮助信息

    import time
    
    def timmer(func):
    
        def wrapper(*args,**kwargs):
            'ssssss'
            start_time=time.time()
            func(*args,**kwargs)   #home(name)
            stop_time=time.time()
            print('run time is %s' %(stop_time-start_time))
        return wrapper
    
    @timmer
    def func(x):
        'fun test'
        print(x)
    
    func(1)
    print(func.__doc__)    ###输出wrapper帮助信息
    #print(help(func))
    
    
    # import time
    # from functools import wraps
    # def timmer(func):
    #     @wraps(func)
    #     def wrapper(*args,**kwargs):
    #         'ssssss'
    #         start_time=time.time()
    #         func(*args,**kwargs)   #home(name)
    #         stop_time=time.time()
    #         print('run time is %s' %(stop_time-start_time))
    #     return wrapper
    #
    # @timmer
    # def func(x):
    #     'fun test'
    #     print(x)
    #
    # func(1)
    # print(func.__doc__)    ###输出wrapper帮助信息
    # #print(help(func))
    
    #输出func帮助信息
    

      

    import time
    from functools import wraps#从函数工具中调用wraps模块
    def timmer(func):
        @wraps(func)#它就可以让你打印出的index.__doc__编程原函数的"dashabi"而不是wrapper函数的"000"
        def wrapper(*args,**kwargs):
            '000'
            start_time=time.time()
            res=func(*args,**kwargs)
            stop_time=time.time()
            print('run time is %s'%(stop_time-start_time))
            return res
        return wrapper
    @timmer
    def index():
        "dashabi"
        print("from index")
    index()
    print(index.__doc__)
    

      

     1 import time          #1
     2 def timmer(func):       #func的值是home的   #3
     3     def wrapper(name):       #4  #7                                 #闭包函数
     4         print(func)           #8
     5         start_time=time.time()      #9
     6         func(name)   #home(name)    #10
     7         stop_time=time.time()       #14
     8         print('run time is %s' %(stop_time-start_time))  #15
     9     return wrapper          #5
    10 @timmer         #home=timmer(home)     #2    #6
    11 def home(name):             #11
    12     time.sleep(2)           #12
    13     print('welcome to %s home page' %name)      #13
    14 home('dragon')      #wrapper('dragon')
    15 
    16 
    17 <function home at 0x0000000000D0E1E0>
    18 welcome to dragon home page
    19 run time is 2.0001142024993896
  • 相关阅读:
    C# 日期格式化
    MVVM框架下,WPF实现Datagrid里的全选和选择
    【转】WPF 给DataGridTextColumn统一加上ToolTip
    C# 获取当前月第一天和最后一天 计算两个日期差多少天
    WPF 弹出UserControl
    斐讯Fir302b救砖教程
    mvc 传递匿名对象
    Java HttpGet
    Java xml object 互转
    HttpClientHandler
  • 原文地址:https://www.cnblogs.com/jiangshitong/p/6697146.html
Copyright © 2011-2022 走看看