装饰器语法糖运用

装饰器语法糖运用

  • 前言:函数名是一个特性的变量,可以作为容器的元素,也可以作为函数的参数,也可以当做返回值。
  • 闭包定义:
    • 内层函数对外层函数(非全局)变量的引用,这个内层函数就可以成为闭包
    • 在Python中我们用__closure__来检查函数是否是闭包
    • def func1():
          name = '张三'
      
          def func2():
              print(name)  # 能够访问到外层作用域的变量
          func2()
          print(func2.__closure__)  # (<cell at 0x1036c7438: str object at 0x10389d088>,)
      
      func1()
      print(func1.__closure__)  # None
  • 装饰器

    • 前言:软件设计原则:开闭原则,又称开放封闭原则

      • 指对扩展代码的功能是开放的,但对修改源代码是封闭的,
    • def create_people():
          print(‘女娲真厉害,捏个泥吹口气就成了人!‘)
      
      def a(func):
          def b():
              print(‘洒点水‘)
              func()
          return b
      
      ret = a(create_people)
      ret()
    • 通过装饰器语法等同于
    • def a(func):
          def b():
              print(‘洒点水‘)
              func()
          return b
      
      @a  # 装饰器语法糖的作用就是上述函数ret()
      def create_people():
          print(‘女娲真厉害,捏个泥吹口气就成了人!‘)
      
      create_people()
  • 装饰带返回值的函数,即return出被装饰函数的执行结果
    • def foo(func):  # 接收的参数是一个函数名
          def bar():  # 定义一个内层函数
              print("这里是新功能...")  # 新功能
              r = func()  # 在内存函数中拿到被装饰函数的结果
              return r  # 返回被装饰函数的执行结果
          return bar
      
      # 定义一个有返回值的函数
      @foo
      def f1():
          return ‘嘿嘿嘿‘
      
      # 调用被装饰函数
      ret = f1()  # 调用被装饰函数并拿到结果
      print(ret)
  • 装饰带参数的函数
    • def func1(func):              # 接收的参数为一个函数名
          def inner(*args, **kwargs):     # 这里需要定义和被装饰函数相同的参数
              print("新功能")                # 新功能
              ret = func(*args, **kwargs)     #被装饰的函数和参数
              print("新功能")
              return ret
          return inner
      
      # 定义一个需要俩个参数的函数
      @func1
      def func(a, b):
          return a + b
      
      ret = func(3, 5)
      print(ret)
  • 带参数的装饰器 即在装饰器外在写一层函数,从而使其带参数
    • def d(a=None):        # 定义一个外层函数,给装饰器传参数
          def func1(func):  # 接收的是一个函数名
              def inner(*args, **kwargs): # 被装饰的函数,和参数
                  if a:
                      print(f"欢迎来到{a}")   #添加新功能
                  else:
                      print("欢迎来到王者荣耀")
                  func(*args, **kwargs)
              return inner
          return func1
      
      # @d("英雄联盟")
      # def func(st):
      #     print(st)
      # func("敌军还有三十秒到达战场")
                                    # 欢迎来到英雄联盟
                                    # 敌军还有三十秒到达战场
      
      @d()
      def func(st):
          print(st)
      func("敌军还有三十秒到达战场")
      # 欢迎来到王者荣耀
      # 敌军还有三十秒到达战场
  • 装饰器修复技术
    • 定义:被装饰的函数最终都会失去本来的__doc__等信息, Python给我们提供了一个修复被装饰函数的工具。
    • from functools import wraps    #导入
      print(f1.__doc__)
      print(f1.__name__)
  • 多个装饰器装饰同一函数
    • def foo1(func):
          print("d1")
      
          def inner1():
              print("inner1")
              return "<i>{}</i>".format(func())
      
          return inner1
      
      def foo2(func):
          print("d2")
      
          def inner2():
              print("inner2")
              return "<b>{}</b>".format(func())
      
          return inner2
      
      @foo1
      @foo2
      def f1():
          return "Hello Andy"
      
      # f1 = foo2(f1)  ==> print("d2") ==> f1 = inner2
      # f1 = foo1(f1)  ==> print("d1") ==> f1 = foo1(inner2) ==> inner1
      
      ret = f1()  # 调用f1() ==> inner1()  ==> <i>inner2()</i>  ==> <i><b>inner1()</b></i> ==> <i><b>Hello Andy</b></i>
      print(ret)
  • 类装饰器
    • class D(object):
          def __init__(self, a=None):
              self.a = a
              self.mode = "装饰"
      
          def __call__(self, *args, **kwargs):
              if self.mode == "装饰":
                  self.func = args[0]  # 默认第一个参数是被装饰的函数
                  self.mode = "调用"
                  return self
              # 当self.mode == "调用"时,执行下面的代码(也就是调用使用类装饰的函数时执行)
              if self.a:
                  print("欢迎来到{}页面。".format(self.a))
              else:
                  print("欢迎来到首页。")
              self.func(*args, **kwargs)
      
      @D()
      def index(name):
          print("Hello {}.".format(name))
      
      @D("电影")
      def movie(name):
          print("Hello {}.".format(name))
      
      if __name__ == ‘__main__‘:
          index(‘张三‘)
          movie(‘张三‘)
  • 装饰类
    • # 定义一个类装饰器
      class D(object):
          def __call__(self, cls):
              class Inner(cls):
                  # 重写被装饰类的f方法
                  def f(self):
                      print(‘Hello 张三.‘)
              return Inner
      
      @D()
      class C(object):  # 被装饰的类
          # 有一个实例方法
          def f(self):
              print("Hello world.")
      
      if __name__ == ‘__main__‘:
          c = C()
          c.f()

原文地址:https://www.cnblogs.com/yuncong/p/9886555.html

时间: 2024-11-05 11:27:32

装饰器语法糖运用的相关文章

python 装饰器语法糖(@classmethod @staticmethod @property @name.)原理剖析和运用场景

引用:http://blog.csdn.net/slvher/article/details/42497781 这篇文章系统的介绍这几者之间的关系和区别.有兴趣的朋友可以到上面的链接查看原文,这里我把原文拷贝如下(如有侵权,通知马上删除) ==================================================================== 在阅读一些开源Python库的源码时,经常会看到在某个类的成员函数前,有类似于@staticmethod或@classme

python装饰器&amp;语法糖

装饰器: 1 >>> def a(func): 2 ... def b(*argv): 3 ... print("in b") 4 ... return func(*argv) 5 ... return b 6 ... 7 >>> def c(a,b): 8 ... print(a**2,b**2) 9 ... 10 >>> c = a(c) 11 >>> c(2,3) 12 in b 13 4 9 14 >

python学习day07 高阶函数 装饰器 语法糖

语法糖对于计算机的运行并没有任何的好处,但是对于程序员的好处是很大的,方便我们写代码,所以称为糖 #******************************装饰器************************* # 装饰器本质上就是一个python函数,他可以让其他函数在不需要做任何代码变动的前提下,增加额外的功能,装饰器的返回值也是一个函数对象. # 装饰器的应用场景:比如插入日志,性能测试,事务处理,缓存等等场景 import time def func1(): print('in f

python装饰器 语法糖

简介: 装饰器(Decorators)是 Python 的一个重要部分.简单地说:他们是修改其他函数的功能的函数. 比如说我们写flask,路由就是用装饰器定义的.如果写权限控制,那么权限控制一般也是由装饰器来实现的.日志记录,一般也可以通过装饰器来实现. 简单说,就是为了给某些函数增加一种或几种功能的做法. 下面举例实现. 一:基本函数 1.源码 from time import sleep def watch_movie(): print('看电影') sleep(3) print('The

python 装饰器(语法糖)

def  login(func):    def testlogin():        for  i in range(3):            _username="abc"            _passwrod="123456"            user_status = False            iuput = input("请输入账号:")            input1 = input("请输入密码

详解create-react-app 2.0版本如何启用装饰器语法

create-react-app(简称cra)已经更新之2.0.3版本, babel也更新至7.x版本, JavaScript装饰器语法虽然还不是标准, 但是借助于babel, 也能在项目里愉快的玩耍. cra2.0时代如何启用装饰器语法呢? 我们依旧采用的是react-app-rewired, 通过劫持webpack cofig对象, 达到修改的目的. ? 1 yarn add react-app-rewired 修改package.json ? 1 2 3 4 5 "scripts"

python装饰器 语法与解读

import time #加载time模块 from functools import wraps #加载functools模块中的wraps函数 def cost_time(old_fn): # 注:cost_time是装饰器名 ,形参old_fn是要装饰的函数 装饰器最外层没有return,也就是不用返回的 @wraps(old_fn) #它主要作用就是接收到原函数中的注析,所以括号内也是上面形参一样的 def inner(*args, **kwargs): # inner它是cost_ti

在create-react-app 中启用装饰器语法

方法一: 暴露create-react-app 配置文件 运行命令: nom run eject 如果报错,说明需要用git 保存当前文件更改后才能使用上面的命令. 运行如下git命令: git init git add ./ git commit -m 'init' 在 babel 中添加 plugins 配置 在 package.json 文件中找到 babel 的配置,添加如下代码即可: "babel": { "presets": [ "react-

闭包函数、装饰器以及语法糖

闭包函数: 1.闭包函数必须在函数内部定义 2.闭包函数可以引用外层函数的名字 闭包函数是 函数嵌套.函数对象.名称空间与作用域 结合体. # 直接传参 def func(x): print(x) func(1000) # 通过闭包函数传参 def outer(number): # number = 100 # inner就是闭包函数 def inner(): print(number) return inner func = outer(1000) # ---> inner地址 ---> f