gpt4 book ai didi

python - 嵌套函数中的局部变量

转载 作者:行者123 更新时间:2023-11-28 19:11:48 29 4
gpt4 key购买 nike

好的,请耐心等待,我知道这看起来会非常复杂,但请帮助我理解发生了什么。

from functools import partial

class Cage(object):
def __init__(self, animal):
self.animal = animal

def gotimes(do_the_petting):
do_the_petting()

def get_petters():
for animal in ['cow', 'dog', 'cat']:
cage = Cage(animal)

def pet_function():
print "Mary pets the " + cage.animal + "."

yield (animal, partial(gotimes, pet_function))

funs = list(get_petters())

for name, f in funs:
print name + ":",
f()

给予:

cow: Mary pets the cat.
dog: Mary pets the cat.
cat: Mary pets the cat.

基本上,为什么我没有得到三种不同的动物? cage 不是被“打包”到嵌套函数的局部作用域中了吗?如果不是,对嵌套函数的调用如何查找局部变量?

我知道遇到这类问题通常意味着一个人“做错了”,但我想了解发生了什么。

最佳答案

嵌套函数在执行时从父范围查找变量,而不是在定义时。

编译函数体,验证“自由”变量(未通过赋值在函数本身中定义),然后将其作为闭包单元绑定(bind)到函数,代码使用索引引用每个单元。 pet_function 因此有 一个 自由变量 (cage),然后通过闭包单元引用它,索引为 0。闭包本身指向局部变量get_petters 函数中的 cage

当您实际调用该函数时,该闭包将用于在您调用该函数时 周围范围内查看 cage 的值。问题就在这里。当您调用您的函数时,get_petters 函数已经计算完它的结果。 cage 局部变量在执行期间的某个时刻被分配给 'cow''dog''cat ' 字符串,但在函数的末尾,cage 包含最后一个值 'cat'。因此,当您调用每个动态返回的函数时,您会打印出值 'cat'

解决方法是不依赖闭包。您可以改用部分函数,创建新函数作用域,或将变量绑定(bind)为关键字参数的默认值。 p>

  • 部分函数示例,使用 functools.partial() :

    from functools import partial

    def pet_function(cage=None):
    print "Mary pets the " + cage.animal + "."

    yield (animal, partial(gotimes, partial(pet_function, cage=cage)))
  • 创建新范围示例:

    def scoped_cage(cage=None):
    def pet_function():
    print "Mary pets the " + cage.animal + "."
    return pet_function

    yield (animal, partial(gotimes, scoped_cage(cage)))
  • 将变量绑定(bind)为关键字参数的默认值:

    def pet_function(cage=cage):
    print "Mary pets the " + cage.animal + "."

    yield (animal, partial(gotimes, pet_function))

不需要在循环中定义scoped_cage函数,编译只发生一次,而不是在循环的每次迭代中。

关于python - 嵌套函数中的局部变量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38940812/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com