3 回答
TA贡献1805条经验 获得超10个赞
您在这里看到的是访问和分配变量之间的区别。在Python 2.x中,您只能分配最内层范围或全局范围内的变量(后者通过使用全局语句完成)。您可以访问任何封闭范围中的变量,但不能访问封闭范围中的变量,然后在最内层或全局范围内分配变量。
这意味着如果对函数内部的名称进行了任何赋值,则在访问名称之前必须已在最内层作用域中定义该名称(除非使用了全局语句)。在您的代码中,该行c += 3基本上等同于以下内容:
tmp = c
c = tmp + 3
因为c函数中有赋值,所以该函数中的每个其他实例c都只会查找本地范围funcB。这就是为什么你看到错误,你试图c获取它的当前值+=,但是在本地范围内c还没有定义。
在Python 3中,您可以通过使用非本地语句来解决此问题,该语句允许您分配不在当前范围内但不在全局范围内的变量。
您的代码看起来像这样,在顶部有一个类似的行funcC:
def funcB():
nonlocal c
c += 3
...
在Python 2.x中,这不是一个选项,唯一可以更改非局部变量值的方法是它是否可变。
最简单的方法是将值包装在一个列表中,然后在之前刚使用过变量名的每个位置修改和访问该列表的第一个元素:
def funcA():
print "funcA"
c = [0]
def funcB():
c[0] += 3
print "funcB", c[0]
def funcC():
c[0] = 5
print "funcC", c[0]
print "c", c[0]
funcB()
funcC()
funcB()
funcC()
print "end"
funcA()
......和输出:
funcA
c 0
funcB 3
funcC 5
funcB 8
funcC 5
end
TA贡献1854条经验 获得超8个赞
在funcB中的'+ ='和funcC中的'='都不能访问'c'吗?
不,funcC
制作一个新变量,也称为c
。=
在这方面是不同的+=
。
要获得您(可能)想要的行为,请将变量包装在单个元素列表中:
def outer(): c = [0] def inner(): c[0] = 3 inner() print c[0]
将打印3
。
编辑:你想要c
作为一个参数传递。Python 2没有其他方法,AFAIK,以获得所需的行为。Python 3 nonlocal
为这些案例引入了关键字。
TA贡献1795条经验 获得超7个赞
1)在funcB和in c
中的两种情况下都没有被访问?+=
=
funcC
不,因为c += 3
和以下一样:
c = c + 3 ^ |and funcB does not know what this c is
2)我没有做的一个选择c
一个全局变量,然后宣布global c
在funcB
。
请不要这样做,只需更改:
def funcB():
有:
def funcB(c):
并funcB(c)
在稍后的代码中调用。
注意:您还应该定义funcB
和funcC
外部的cosiderfuncA
添加回答
举报