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

     一 装饰是什么

    装饰器是 闭包函数的一种应用,只不过其传递的是函数。装饰器的返回值也是一个函数对象。

    装饰器原则:

    装饰器原则:1、不修改被装饰对象的 源代码  
                   2、不修改被装饰对象的 调用方式
    
    达到的目标: 在遵循1和2的前提下,为被装饰对象添加新功能        

     

    简而言之:@a 就是将 b 传递给 a(),并返回新的 b = a(b)

    import time
    
    def timer(func):
        def internal(*args,**kwargs):
            start_time = time.time()
            res = func(*args,**kwargs)
            stop_time = time.time()
            print('run time is {}'.format(stop_time - start_time))
            return res
        return internal
    
    
    @timer            #相当于 test = timer(test)
    def test():
        time.sleep(3)
        print('Hello World')
    
    test()
    
    
    #结果:
    # Hello World
    # run time is 3.0008761882781982

    二 装饰器的使用:

    import time
    
    def timer(func):
        def internal(*args,**kwargs):
            start_time = time.time()
            res = func()
            stop_time = time.time()
            print('run time is {}'.format(stop_time - start_time))
            return res
        return internal
    
    @timer
    def test():
        time.sleep(3)
        print('from test')
    
    test()
    无参装饰器
    def auth2(auth_type):
        def auth(func):
            def internal(*args,**kwargs):
                if auth_type == 'file':
                    name = input('username:')
                    pwd = input('password:')
                    if name == 'tom' and pwd == '123':
                        print('Auth Success')
                        res = func(*args,**kwargs)
                        return res
                    else:
                        print('Auth error')
                elif auth_type == 'sql':
                    print('sql 先停停')
            return internal
        return auth
    
    @auth2(auth_type='file')
    def index():
        print('Hello')
    
    index()
    有参装饰器

     

    三 wrapper返回的不是原函数的帮助信息

    当我们使用了装饰器的时候,虽然没有修改代码本身,但是在运行的时候,比如上面这个例子,运行index其实在运行internal了,如果我们打印my_index的注释信息,会打印internal的注释信息,那么该如何处理?

     
    import time
    
    def timer(func):
        def internal():
            """计算运行时间"""
            stat_time = time.time()
            res = func()
            stop_time = time.time()
            print('run time is {}'.format(stop_time - stat_time))
            return res
        return internal
    
    @timer
    def index():
        """世界 你好"""            #原始注释信息
        print('Hello World')
    
    index()
    print(index.__doc__)
    
    
    #结果:
    Hello World
    run time is 0.0
    计算运行时间               #并不是想要的 
    
    
    
    
    
    
    
    

    解决方法:

    import time
    from functools import wraps
    
    def timer(func):
        @wraps(func)
        def internal():
            """计算运行时间"""
            stat_time = time.time()
            res = func()
            stop_time = time.time()
            print('run time is {}'.format(stop_time - stat_time))
            return res
        return internal
    
    @timer
    def index():
        """世界 你好"""
        print('Hello World')
        time.sleep(1)
    
    index()
    print(index.__doc__)
    
    
    #结果:
    Hello World
    run time is 1.0004730224609375
    世界 你好
    
    
    
  • 相关阅读:
    亿级流量架构服务降级,写得太好了!
    面试官:什么是对象池?有什么用?别说你还不会!
    最新数据库排行榜出炉!MySQL 稳了~
    别再写满屏的 get & set 了,太 Low!试试 MapStruct 高级玩法!
    vista 中php4, php5 共存
    dotnet framework 3.5 installed issues on nonenglish os
    web service notes
    msn web status
    db notes
    wikipedia的mysql utf8中文在.net中的处理
  • 原文地址:https://www.cnblogs.com/zhaochangbo/p/6691813.html
Copyright © 2011-2022 走看看