zoukankan      html  css  js  c++  java
  • 闭包 与 装饰器

    1. 函数参数
      1. 函数名存储了函数所在的空间地址
      2. 函数名+ () 到函数所在的空间执行里面的代码
    2. 闭包:
      1. 发生函数嵌套
      2. 外层函数的返回值是内层函数的函数名(地址/引用)
      3. 外层函数有参数(内层函数使用到)
      4. 节省系统资源  提高代码复用率的一种特殊语法
      5. 语法格式
        1. def  外层函数(参数):
              def 内层函数():
                  pass
              return 内层函数
      6. 闭包流程
        1. 执行第五行 调用func_out 
        2. 执行2,3 行 func_in函数 只定以不执行  开辟一个空间 暂且定为   0x11(),所以func_in=0x11
        3. 执行第四行  返回func_in 也就是0x11
        4. 然后到第五行 usa_rate= func_in= 0x11
        5. 执行第六行 0x11(100)  =  fun_in()
        6. 执行2,3 行代码
          1.   
            1 1.def func_out(rate):
            2 2.   def func_in(money):
            3 3.        print(rate * money)
            4  
            5 4.    return func_in
            6  
            7 5.usa_rate = func_out(0.7)
            8 6.usa_rate(100)
            
     
     
    • nonlocal    ------   声明外层函数的变量
    1. 装饰器  
      1. 在不改变原有代码的前提下  还可以给函数增加新的功能
      2. 使用方法
        1. @新加功能的函数名
        2. 装饰器下面正好是函数
        3. 自动执行 login = func_out(login)
        4. 执行流程
          1. 执行第六行,首先装饰器会自动执行一句话 login = func_out(login)
          2. 把7,8行代码开辟一个空间地址暂且叫做0x22, 当作参数传给第一行func
          3. 执行第一行   0x22传递给func
          4. 2,3,4函数只定以不执行开辟一个空间地址  暂且是 0x11
          5. 执行第五行  返回func_in  = =0x11 给函数调用者,  也就是 login = func_in== 0x11
          6. 然后执行login() == 0x11()==func_in(),到2,3,4代码  
          7. 第四行  func() == login ==0x22=7,8行代码
        5. *** 执行流程结论***
          1. func ==> 原始login  也就是0x22
          2. 新的login()0x11 ==>func_in()
          3. 1.def func_out(func):
            2.    def func_in():
            3.        print("验证")
            4.        func()
            5.    return func_in
            6.@func_out
            7.def login():
            8.    print("登录")
            9.login()
     
    1. 通用版装饰器
     
    def func_out(func):
        def func_in(*args,**kwargs):
            return func(*args,**kwargs)
     
        return func_in
     
    @func_out
    def login(*args,**kwargs):
        print(args)
        print(kwargs)
     
     
     
    login(10,30,age = "123",name = "qwe")
    1. 多重装饰器
      1. 执行流程
        1.  
          1.def func_out01(func01):
          2.    print("func_out01 is show")
          3.    def func_in01():
          4.        print("func01 is show")
          5.        func01()
          6.    return func_in01
          7.def func_out02(func02):
          8.    print("func_out02 is show")
          9.    def func_in02():
          10.        print("func02 is show")
          11.        func02()
          12.   return func_in02
          13.@func_out02
          14.@func_out01
          15.def login():
          16.    print('login is show')
          17.login()
           
          答案:
          func_out01 is show
          func_out02 is show
          func02 is show
          func01 is show
          login is show
           
           
        2. 首先执行13行 装饰器func_out02下面不是函数,所以执行14行,
        3. 把15.16行开辟一个空间暂且定义为0x11 ,把0x11当作参数传递给func01暂且存起来
        4. 执行func_out01,自动执行login = func_out(login)  login = 0x11 = func01
        5. 执行第二行  得出第一个结果 --- func_out01  is show
        6. 3,4,5只定以不执行 开辟一个空间 暂且定义以为  0x22
        7. 返回 0x22    新login = 0x22 = func_in01
        8. 14行变为一个函数
        9. 执行装饰器13行  自动执行 0x22=func_in01 == func_out02(0x22)
        10. 执行10行  func_in01 = func02 = 0x22   得出第二个结果 ----- func_out02  is show
        11. 把9,10,11  封装起来  开辟一个空间 称为  0x33 
        12. 执行12行  返回给函数调用者  login = func_in02()
        13. 这时候执行login()
        14. 执行9,10,11 行代码得出 第三个结果---  func02  is show
        15. 执行11行  fun02() = func_in01()-----得出func01  is  show
        16. 执行fun01()  得出  ==  login   is   show       fun01() = login
     
  • 相关阅读:
    利用WebClient实现自动添写、提交表单
    动态.net代码生成器遇到的问题
    unicode
    使用using清理非托管资源
    C#中解决插入数据库的某个字段类型为datetime 为空
    JQuery中根据属性或属性值获得元素
    Access 的top和order by 的问题
    JavaScript escape() 函数
    Asp.net嵌套
    合并程序集时出错的问题ILMerge.Merge.ERROR...
  • 原文地址:https://www.cnblogs.com/ZT-GJ/p/9693458.html
Copyright © 2011-2022 走看看