python
中赋值操作都会在当前作用域的locals()
内部新绑定一个变量。因此如下的代码会报错:
def func1():
x = 1
print locals()
def func2():
print 'fun2:', locals()
x += x
print 'fun2:', locals()
func2()
print locals()
if __name__ == '__main__':
func1()
报错就是
UnboundLocalError: local variable 'x' referenced before ssignment
但是为什么把x
改成列表,然后以下面的方式:
def func1():
x = [1, 2, 3]
print locals()
def func2():
print 'fun2:', locals()
x[0] += x[0]
print 'fun2:', locals()
func2()
print locals()
if __name__ == '__main__':
func1()
输出是:
{'x': [1, 2, 3]}
fun2: {'x': [1, 2, 3]}
fun2: {'x': [2, 2, 3]}
{'func3': <function func3 at 0x7f89da00ac08>, 'x': [2, 2, 3], 'func2': <function func2 at 0x7f89da00ab90>}
但是如果把x[0] += x[0]
改成x = x[0]
又报错了。
求解释啊。。。已经懵了---
func2는 func1 내에 있고 그 범위는 클로저와 동일합니다(클로저가 무엇인지에 대해서는 내 기사: Python의 클로저 및 데코레이터 참조). 따라서 x는 실제로 상위 함수에 있습니다. func1의 범위 내에서 다음을 호출합니다. func2를 사용하는 것은 func1을 사용하여 전역 변수를 호출하는 것과 비슷합니다. x를 읽을 수만 있고 직접 다시 쓸 수는 없습니다. 하지만 리스트 객체의 x를 사용하면 x[0]은 x 객체가 아니라 x의 요소이므로 재정의될 수 있습니다.
으아악사실 이건 파이썬 2의 버그입니다. 파이썬 3에서 nonlocal 문이 도입되었습니다. global 문과 비슷하지만 특정 변수가 부모 함수의 변수임을 선언하는 데 사용됩니다. 하위 함수는 변수를 직접 다시 작성할 수 있습니다.
Python 2에서는 목록 개체만 사용할 수 있지만 Python 3에서는 다음과 같이 작성할 수 있습니다.
자세한 내용은 여기를 참조하세요
해결되었습니다. 아이디어는 첫 번째 답변과 댓글을 참조하세요.