[英]python closure weird behavior
我正在尝试使用Lexical闭包中的问题编写一段代码
flist = []
for i in xrange(3):
def func(x): return x*i
flist.append(func)
for f in flist:
print f.func_closure
输出是:
None
None
None
不应该吗?:
(<cell at 0x9222d94: int object at 0x8cabdbc>,)
(<cell at 0x9222d94: int object at 0x8cabdbc>,)
(<cell at 0x9222d94: int object at 0x8cabdbc>,)
我使用以下代码获得了以上输出:
flist = []
def actualFact():
for i in xrange(3):
def func(x): return x * i
flist.append(func)
for f in flist:
print f.func_closure
我正在使用Python 2.6.6(r266:84292,2010年9月15日,15:52:39)。
仅当在全局(模块)范围之外引用变量时才引入闭包:
>>> def foo():
... def bar(): pass
... return bar
...
>>> foo().func_closure is None
True
>>> spam = 'eggs'
>>> def foo():
... def bar(): return spam
... return bar
...
>>> foo().func_closure is None
True
仅当内部函数引用周围范围中的变量时,才会生成闭包:
>>> def foo():
... spam = 'eggs'
... def bar(): return spam
... return bar
...
>>> foo().func_closure is None
False
>>> foo().func_closure
(<cell at 0x108472718: str object at 0x108471de0>,)
请注意,您实际上必须在周围的范围内引用变量。 只需忽略范围,您None
一次None
:
>>> def foo():
... spam = 'eggs'
... def bar(): pass
... return bar
...
>>> foo().func_closure is None
True
在您的第一个示例中, i
是一个模块作用域变量,仅在您的第二个示例中,您才通过将代码包装在新的函数actualFact
引入新的作用域。
语言参考将func_closure
指定为“ None或包含函数自由变量绑定的单元格元组”。
现在,请注意两个版本之间的区别:在第一个版本中, i
是模块级(即全局)变量。 评估每个功能的结果是相同的:
>>> [f(2) for f in flist]
[4, 4, 4]
在每个函数中, i
都不是自由的,而是引用全局i
,因此不,输出不应是非零长度元组的列表。
在实践中,除非您正在做一些相当深的魔术,否则您可能并不关心func_closure
的值。 如果您正在做一些魔术,请注意给定的规范,如果没有自由变量,似乎没有充分的理由为什么func_closure
不应该为空元组,因此,如果您希望代码在偶数之间可移植,则应适当地处理这种情况。不同的python版本。
无需关闭即可完成此操作的廉价方法
for i in xrange(3):
def func(x, i=i): return x*i
flist.append(func)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.