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

    装饰器
    1.什么是装饰器?
      装饰器指的是为被装饰对象添加新功能的工具
      装饰器本身可以是任意可调用对象
      被装饰对象本身也可以是任意可调用对象
    2.为何要用 装饰器
      开放封闭原则:对修改封闭,对扩展开放
      装饰器的实现原则:
        1.不能修改被装饰对象的源代码
        2.不能修改被装饰对象的调用方式
      装饰器的目的:
        就是在遵循原则1和2的前提下为被装饰对象添加新功能
    3.如何使用
      import time
      def index():
        time.sleep(1)
        print('welcome to index page')
      index()
      #统计运行时间
      思路1
      import time
      def index():
        start=time.time()
        time.sleep(1)
        print('welcome to index page')
        stop=time.time()
        print('run time is %s'%(stop - start))
      index()
      修改了源代码

      思路2
      import time
      def index():
        time.sleep(1)
        print('welcome to index page')
      start=time.time()
      index()
      stop=time.time()
      print('run time is %s' %(stop - start))
      不能重复使用,下面我们将它写在一个函数里面

      思路3
      import time
      def index():
        time.sleep(1)
        print('welcome to index page')
      def wrapper():
        start=time.time()
        index()
        stop=time.time()
        print('run time is %s' %(stop - start))
      wrapper()
      可以重复调用但是写死了,只能修饰index,下面我们要将其写活,将index换成func

      思路4:
      import time
      def index():
        time.sleep(1)
        print('welcome to index page')
      def wrapper():
        start=time.time()
        func()
        stop=time.time()
        print('run time is %s' %(stop - start))
      wrapper()
      函数体需要外部传进来参数,两种解决方案 1.直接传参 2.闭包函数

      直接传参:
      import time
      def index():
        time.sleep(1)
        print('welcome to index page')
      def wrapper(func):
        start=time.time()
        func() #index()
        stop=time.time()
        print('run time is %s' %(stop - start))
      wrapper(index)
      本来使用index()调用的,这个直接改变了人家的调用方式违反了开放封闭原则

      闭包函数:
      import time
      def index():
        time.sleep(1)
        print('welcome to index page')
      def timer(func):
        #func=最原始index的内存地址
        def wrapper():
          start=time.time()
          func() #func=最原始index的内存地址
          stop=time.time()
          print('run time is %s' %(stop - start))
        return wrapper
      index=timer(index) #翻译一下:index=(timer(最原始index的内存地址)) #index=wrapper的内存地址
      index() #wrappper的内存地址()

      思路5:完善这个装饰器
      如果有返回值:
      import time
      def index():
        time.sleep(1)
        print('welcome to index page')
        return 1234
      def timer(func):
        def wrapper():
          start=time.time()
          res=func()
          stop=time.time()
          print('run time is %s' %(stop - start))
          return res
        return wrapper
      index=timer(index)
      res=index()
      print(res)

    如果还有其他函数被装饰:
      import time
      def index():
        time.sleep(1)
        print('welcome to index page')
        return 1234
      def home(name):
        time.sleep(1)
        print('welcome %s to home page' %name)
      def timer(func):
        def wrapper(*args,**kwargs):
          start=time.time()
          res=func(*args,**kwargs)
          stop=time.time()
          print('run time is %s' %(stop - start))
          return res
        return wrapper
      index=timer(index)
      index()
      home=timer(home)
      home('egon')

      思路6:语法糖 在被装饰对象正上方单独一行写上@装饰器的名字
      import time
      def timer(func):
        def wrapper(*args,**kwargs):
          start=time.time()
          res=func(*args,**kwargs)
          stop=time.time()
          print('run time is %s' %(stop - start))
          return res
        return wrapper
      @timer 作用:#index=timer(index) #翻译一下:index=(timer(最原始index的内存地址)) #index=wrapper的内存地址
      def index():
        time.sleep(1)
        print('welcome to index page')
        return 1234
      @timer
      def home(name):
        time.sleep(1)
        print('welcome %s to home page' %name)
      index()
      home('egon')

      装饰器模板:
      def outter(func):
        def wrapper(*args,**kwargs):
        res=func(*args,**kwargs)
        return res
      return wrapper


  • 相关阅读:
    Java实现 LeetCode 455 分发饼干
    Java实现 LeetCode 455 分发饼干
    Java实现 LeetCode 455 分发饼干
    Java实现 LeetCode 454 四数相加 II
    Java实现 LeetCode 454 四数相加 II
    Java实现 LeetCode 454 四数相加 II
    FFmpeg解码H264及swscale缩放详解
    linux中cat more less head tail 命令区别
    C语言字符串操作总结大全(超详细)
    如何使用eclipse进行嵌入式Linux的开发
  • 原文地址:https://www.cnblogs.com/lizeqian1994/p/10040019.html
Copyright © 2011-2022 走看看