Python 闭包

在介绍Python中闭包的知识点之前,我们首先来了解一下什么是全局变量局部变量
1.全局变量:在函数体外部声明的变量,所有函数都可以访问;
2.局部变量:在函数体内部声明的变量,仅限于函数内部使用;

在Python中全局变量和局部变量有以下几点关系:

  1. 当局部变量和全局变量名称相同时,采用就近原则;
  2. 如果全局变量是不可变的(比如字符串),在函数中进行修改需要添加global关键字;
  3. 如果全局变量是可变的(比如列表),在函数中修改的时候就不需要添加global,可直接修改;
  4. locals()查看本地变量有哪些,以字典的形式输出;
  5. globals()查看全局变量有哪些,以字典的形式输出(注意里面会有一些系统的键值对)。
name = 'xiaoming'        # 不可变
list = [1, 2, 3, 4, 5]   # 可变
def func():
    global name          # 修改全局变量,则需在函数内部声明:global 变量名
    names = 's'          # 局部变量
    print(name)
    name += 'ming'
    print('修改后的name是:', name)
    # 修改列表
    list.append(6)
    print(list)
   
>>>修改后的name是: xiaomingmings
>>>[1, 2, 3, 4, 5, 6]

在了解全局变量和局部变量后我们再来了解一下什么是函数嵌套
函数嵌套就是在函数里面定义函数,我们称定义在函数内部的函数为内部函数,其外部的函数为外部函数。
其具有以下特点:
1.可以访问外部函数的变量;
2.内部函数可以修改外部函数的可变类型的变量;
3.内部函数修改全局的不可变变量时,需要在内部函数声明global关键字
内部函数修改外部函数的不可变的变量时,需要在内部函数中声明 nonlocal关键字
下面我们通过一个简单的示例来深入的了解一下内部函数和全局、局部变量之间的关系:

N = 10                     # 全局变量
def func_1():
    n = 5                  # 局部变量
    list_1 = [3, 6, 9, 4]  # 局部变量
                           # 声明内部函数
    def inner_func():
        nonlocal n         # 修改外部函数变量
        global N           # 修改全局变量
        n = 100
     					   # 对list_1里面的元素进行+100操作
        for index, i in enumerate(list_1):
            list_1[index] = i + n
        list_1.sort()  # 排序
        N +=101        # 修改全局变量
       	print(N)
    
    inner_func()           # 调用内部函数
    print(list_1)

func_1()
>>> 111
>>>> [103, 104, 106, 109]

在介绍完全局、局部变量和嵌套函数后,我们开始进入今天的正题------> 闭包

形成闭包条件
1.外部函数中定义了内部函数
2.外部函数是有返回值
3.返回的值是:内部函数名
4.内部函数引用了外部函数的变量
格式:

def 外部函数():
    ...
    def 内部函数():
        ...
    return 内部函数

下面来看一个示例:

def func_2():
    a = 1
    def inner_func():
        b = 2
        print(a,b)
    return inner_func
f = func_2()  # f就是内部函数,f()就表示调用函数
f()
>>>1 2

def func_3(a,b):
    c = 3
    def inner_func():
        s = a + b + c
        print('相加之后的结果是:', s)
    return inner_func
# 调用func_3
# ifunc 就是inner_func()   ifunc = inner_func
ifunc = func_4(1,2)       # a=1,b=2 --> inner_func -->返回内部函数
# 此时返回的内部函数已经记录此时的a和b的值,所以不会受到a,b改变的影响
# 再去调用a=2,b=8 保存在本次的inner_func函数中,返回的时候返回的就是保存2,8的内部函数
ifunc_1 = func_4(2,8) # a=2,b=8 --> inner_func -->返回内部函数
# 调用返出来的内部函数
ifunc()
ifunc_1()
>>>相加之后的结果是: 6
>>>相加之后的结果是: 13

闭包的缺点:
1.作用域没有那么直观
2.因为变量不会回收,所以有一定的内存占用问题
闭包的作用:
1.可以使用同级的作用域
2.读取其他元素的内部变量
3.延长作用域
闭包总结:
1.闭包似优化了变量,原来需要类对象完成的工作,闭包也可以完成
2.由于闭包引用了外部函数的局部变量,则外部函数局部变量没有及时释放,消耗内存
3.闭包使代码变得简洁,便于代码阅读
4.闭包是理解装饰器的基础

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值