函数对象、闭包函数
【一】函数对象
- 函数对象指的是函数可以被当做数据来处理,具体可以分为四个方面的使用
【1】可以直接被引用
定义一个函数用一个新的变量名来存,用新的变量名来调用
# 定义一个函数
def add(x, y):
return x + y
# 将函数地址绑定给一个变量
func = add
# 通过这个变量找到对应的地址,从而调用函数
res = func(1, 2)
print(res) # 3
【2】可以作为元素被存储
功能字典中的函数地址
def add(x, y):
return x + y
dic = {'add': add, 'max': max}
print(dic) # {'add': <function add at 0x0000020523843E20>, 'max': <built-in function max>}
res = dic['add'](1, 2)
print(res) # 3
【3】函数可以作为参数传递给另外一个函数
将函数的内存地址作为参数传递
def add(x, y):
return x + y
def foo(x, y, func):
return func(x, y)
res = foo(1, 2, add)
print(res) # 3
【4】函数的返回值可以是函数
我们直接将函数的内存地址返回
def add(x, y):
return x + y
def bar():
return add
func = bar()
print(func) # <function add at 0x00000239EC363E20>
res = func(1, 2)
print(res) # 3
【二】闭包函数
【1】什么是闭包函数
- 闭包函数就是对外部作用域有引用的函数
- 内嵌函数对外部函数作用域有引用,那这个内嵌函数就叫闭包函数
# 定义全局变量
x_global = 1
def outer():
# 定义局部变量,覆盖全局变量
x_global = 2
def inner():
# 打印外部函数的局部变量
print(x_global)
return inner
func = outer()
func()
# 结果为2
【2】闭包函数的应用
[1]将值以参数的形式传入
import requests
# 将值以参数的形式传入
def get(url):
return requests.get(url).text
[2]将值包给函数
import requests
# 将值包给函数
def page(url):
def get():
return requests.get(url).text
return get
[3]对比
- 方式一在下载同一页面时需要重复传入url
- 方式二只需要传一次值,就会得到一个包含指定url的闭包函数,以后调用该闭包函数无需再传url
import requests
# 将值以参数的形式传入
def get(url):
return requests.get(url).text
# 方式一下载同一页面
get('https://www.python.org')
get('https://www.python.org')
get('https://www.python.org')
import requests
# 将值包给函数
def page(url):
def get():
return requests.get(url).text
return get
# 方式二下载同一页面
python = page('https://www.python.org')
python()
python()
python()
【3】函数工厂
- 闭包允许创建函数工厂,即可以动态生成函数。
import requests
# 将值包给函数
def page(url):
def get():
return requests.get(url).text
return get
python = page('https://www.python.org')
java = page('https://www.java.com')
【4】封装
- 闭包可以用来实现类似面向对象编程中的封装概念
- 通过将函数和其相关的状态(变量)捆绑在一起,形成一个封闭的单元。
def counter():
count = 0
def increment():
nonlocal count
count += 1
return count
return increment
counter1 = counter()
counter2 = counter()
print(counter1()) # 1
print(counter1()) # 2
print(counter2()) # 1