Python 中的闭包以一种“奇怪”的方式表现,可以这么说。考虑以下代码片段,其中我尝试基于foo
两种方式构建闭包列表: 在bad_closure
中,闭包是“动态”构建的,而在good_closure
闭包中是由辅助函数构建的:
def foo(d):
return d + 1
def bad_closure():
''' shares resources implicitly '''
# list of 5 closures
# `i` is shared between all closures
cls = [lambda : foo(i) for i in range(5)]
return cls
def good_closure():
''' no resource sharing '''
def mk_cl(i):
''' helper to make a closure'''
c_ = lambda : foo(i)
return c_
# list of 5 closures
# each closure has its own `i`
cls = [mk_cl(i) for i in range(5)]
return cls
#--- TEST ---
bs = bad_closure()
print([f() for f in bs]) # output: [5, 5, 5, 5, 5]
gs = good_closure()
print([f() for f in gs]) # output: [1, 2, 3, 4, 5]
结果惊人地不同。似乎在 中bad_closure
,闭包每个都有一个固定值 i
,但它们都共享相同 的i
内容,每次迭代都会更新(最后取值5
)!相反, in good_closure
,i
是分开的——正如我所料。
我想看看幕后发生了什么以及为什么。