我理解Python中的局部变量和全局变量的概念,但我只想问为什么在下面的代码中会出现错误。Python逐行执行代码,所以在读取第5行之前不知道a是局部变量。Python在尝试执行第5行后是否返回一行并将其标记为错误?
a=0
def test():
print a #line 4, Error : local variable 'a' referenced before assignment
a=0 #line 5
test()发布于 2014-03-16 16:57:57
设置和测试
为了分析您的问题,让我们创建两个独立的测试函数来复制您的问题:
a=0
def test1():
print(a)
test1()打印0。因此,调用此函数没有问题,但在下一个函数上:
def test2():
print(a) # Error : local variable 'a' referenced before assignment
a=0
test2()我们得到一个错误:
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 2, in test2
UnboundLocalError: local variable 'a' referenced before assignment反汇编
我们可以分解这两个函数(第一个Python2):
>>> import dis
>>> dis.dis(test1)
2 0 LOAD_GLOBAL 0 (a)
3 PRINT_ITEM
4 PRINT_NEWLINE
5 LOAD_CONST 0 (None)
8 RETURN_VALUE 我们看到第一个函数自动加载全局a,而第二个函数:
>>> dis.dis(test2)
2 0 LOAD_FAST 0 (a)
3 PRINT_ITEM
4 PRINT_NEWLINE
3 5 LOAD_CONST 1 (0)
8 STORE_FAST 0 (a)
11 LOAD_CONST 0 (None)
14 RETURN_VALUE 考虑到a是在其内部分配的,所以尝试从局部变量(作为优化问题,函数在运行前被预先编译成字节码)进行LOAD_FAST。
如果我们在Python3中运行它,我们会看到几乎相同的效果:
>>> test2()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 2, in test2
UnboundLocalError: local variable 'a' referenced before assignment
>>>
>>> import dis
>>> dis.dis(test1)
2 0 LOAD_GLOBAL 0 (print)
3 LOAD_GLOBAL 1 (a)
6 CALL_FUNCTION 1 (1 positional, 0 keyword pair)
9 POP_TOP
10 LOAD_CONST 0 (None)
13 RETURN_VALUE
>>> dis.dis() # disassembles the last stack trace
2 0 LOAD_GLOBAL 0 (print)
--> 3 LOAD_FAST 0 (a)
6 CALL_FUNCTION 1 (1 positional, 0 keyword pair)
9 POP_TOP
3 10 LOAD_CONST 1 (0)
13 STORE_FAST 0 (a)
16 LOAD_CONST 0 (None)
19 RETURN_VALUE 我们看到我们的错误再次出现在LOAD_FAST上。
发布于 2014-03-16 17:03:11
Python不会在您提交的函数代码中逐行执行。它首先要把它解析为一个执行的整体。它决定一个变量是本地的还是全局的,这取决于它是在(函数)本地级别写的。根据实际情况,它决定变量是本地的,因此出现了错误。
发布于 2014-03-16 16:54:54
这是因为,在python中,需要告诉您要修改全局变量的值。你这样做是为了:
def test():
global a
print a #line 4, Error : local variable 'a' referenced before assignment
a=0 #line 5使用global a,您可以修改函数中的变量。您可能想看看以下内容:
https://stackoverflow.com/questions/22439752
复制相似问题