代码之家  ›  专栏  ›  技术社区  ›  user29008294

为什么闭包在Python中是这样工作的?

  •  0
  • user29008294  · 技术社区  · 7 月前

    我不太明白闭包在Python中是如何工作的。它的行为出乎意料,我无法理解。

    def A():
        b = 1
        def B():
            b += 1
            return b
        return B()
    print(A())
    

    这会导致UnboundLocalError:在赋值之前引用了局部变量“b”。

    但是 b 实际上是B的闭包,如下例所示。

    def A():
        b = 1
        def B():
            return b + 1
        return B()
    print(A())
    

    因此,在我看来,B的闭包在声明B时创建了环境{B->1}。为什么我不能在本地更新它?

    1 回复  |  直到 7 月前
        1
  •  0
  •   John Bayko    7 月前

    帕特里克·罗伯茨评论中的信息几乎涵盖了这一点。

    但更清楚的是,内部函数可以从封闭作用域读取变量,但不能对其进行写入,除非您声明该变量已经存在(非局部或全局关键字)。否则,写入一个变量会隐式地声明它是局部的,在b+=1的情况下,会尝试读取一个未初始化的局部变量并将其加1,但失败了。

    至于为什么,当捕获一个局部值时,它会变成一个常数,这允许用不同的值构造内部函数。例如:

    def f(x):
      def g():
        print(x)
      return g
    
    print_yes = f('yes')
    print_no = f('no')
    

    打电话 print_yes() 将始终打印“是”,呼叫 print_no() 将打印“否”,即使参数 x 不再存在。