看下面这段简单的代码:
class A(object):
numbers = [1, 2, 3]
numberscopy = numbers[:]
print(*(a for a in numberscopy))
print(*(a for a in numberscopy if a in numbers))
我在类中定义了numbers
变量。然后,我可以使用它来做其他事情,比如制作一个副本,迭代它,并打印它的内容。
但是使用for
-if
语句的最后一行使用NameError: global name 'numbers' is not defined
失败。不是numberscopy
,只是numbers
。
我在python 2.7.14+ (导入了print_function
)和3.7.0上都进行了测试,结果相同。
这一切为什么要发生?它是这样工作的吗?
发布于 2019-05-14 03:11:19
在Python中,class- code中的代码有些混乱。与其说它是一个bug,不如说它是一个“变得奇怪的实现问题”。
问题是:代码通常在模块级运行,或者在函数内部运行-当在函数内部时,有定义良好的“局部”变量。
类体中的代码也在“局部”作用域中运行--但是如果创建的函数是在处理类体时运行的,那么这些函数就不会“看到”外部级别的变量。和生成器表达式,以及理解(在Python3中,Python2是另一种语言,它即将被淘汰,让我们不要把事情复杂化)。用于在生成器内部创建for
迭代器的表达式在“看到”外部变量的作用域中运行。主表达式和if表达式本身都在生成器中,无法“看到”这些变量。
因此,如果在类体中需要理解,一种变通方法是在类体中有一个中间函数,只需生成所需的值和变量,并使用该内部函数的本地命名空间调用它并更新类自己的变量:
class A:
def create_vals():
numbers = [1, 2, 3]
numbers_copy = numbers[:]
values = list(a for a in numbers if a in numbers_copy)
return locals()
locals().update(create_vals())
del create_vals
因此,在临时create_vals
函数(它不是一个方法)中,通常的作用域-嵌套规则适用-在最后两行中,我们将创建的变量复制到类本身,并删除临时函数。
https://stackoverflow.com/questions/56118321
复制相似问题