鱼C论坛

 找回密码
 立即注册

第020讲:函数:内嵌函数和闭包

已有 216 次阅读2018-4-8 21:27 |个人分类:零基础入门python课后习题

0.如果希望在函数中修改全局变量的值,应该使用global关键字。
例如:
>>>count = 5
>>>def MyFun():
global count
count = 10
print(count)
>>>MyFun()
10
>>>count
10

1.在嵌套的函数中,如果希望在内部函数修改外部函数的局部变量,应该使用nonlocal关键字。
例如:
>>>def Fun1():
x=5
def Fun2():
nonlocal x
x*=x
return x
return Fun2()
>>>Fun1()
25

2.Python的函数可以嵌套,但要注意访问的作用域问题,请问以下代码存在什么问题?
def outside():
print('I am outside!')
def inside():
print('I am inside!')
inside()

问题:使用嵌套函数要注意一点就是作用域问题,inside()函数是内嵌在outside()函数中的,所以inside()是除了outside()可以调用,在外边或者别的函数体里是无法对其进行调用的。

正确的调用应该是:
def outside():
print('I am outside!')
def inside()
print('I am inside!')
inside()
outside()

3.请问为何代码A没有报错,但是代码B却报错了?应该如何修改?
代码A:
def outside():
var = 5
def inside():
var = 3
print(var)

inside()
outside()

代码B:
def outside():
var = 5
def inside():
print(var)
var = 3

inside()
outside()

报错原因:这里outside()函数里有一个var变量,但要注意的是,内嵌函数inside()也有一个同名的变量,python为了保护变量的作用域,故将outside()的var变量屏蔽起来,因此此时是无法访问到外层的var变量的。应该修改为:
>>>def outside():
var = 5
def inside():
nonlocal var
print(var)
var = 8

inside()
>>>outside()
此时输出为5,是不是感到奇怪,为何输出的不是8呢?因为,先打印的时候,var还没有被赋新值,仍然是外部的5,如果将后面再加一句,改为下面的,就不一样了:
>>>def outside():
var = 5
def inside():
nonlocal var
print(var)
var = 8
print(var)

inside()
>>>outside()
此时,输出5和8.
4.请问如何访问funIn()呢?
def funOut():
def funIn():
print('宾果!你成功访问到我啦!')
return funIn()

只需要直接调用funOut()即可:
funOut()
宾果!你成功访问到我啦!

5.请问如何访问funIn()呢?
def funOut():
def funIn():
print('宾果!你成功访问到我啦!')
return funIn

区别于上一题,这里你就需要用funOut()()访问啦:
funOut()()
宾果!你成功访问到我啦!

当然也可以“曲线救国”:
go = funOut()
go()
宾果!你成功访问到我啦!

6.以下是“闭包”的一个例子,请你目测下会打印什么内容?
def funX():
x = 5
def funY():
nonlocal x
x +=1
return x
return funY
a = funX()
print(a())
print(a())
print(a())

会打印:
6
7
8

因为,当a = funX()的时候,只要a变量没有被重新赋值,funX()就没有被释放,也就是说局部变量x就没有被重新初始化。所以当全局变量不适用的时候,可以考虑使用闭包更稳定和安全。




路过

雷人

握手

鲜花

鸡蛋

评论 (0 个评论)

facelist

您需要登录后才可以评论 登录 | 立即注册

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2025-7-14 00:59

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

返回顶部