Python范围规则究竟是什么?
如果我有一些代码:
code1
class Foo:
code2
def spam.....
code3
for code4..:
code5
x()
Run Code Online (Sandbox Code Playgroud)
在哪里x找到?一些可能的选择包括以下列表:
在执行期间,当函数spam在其他地方传递时,也存在上下文.也许lambda函数的传递方式有点不同?
某处必须有简单的参考或算法.对于中级Python程序员来说,这是一个令人困惑的世界.
编辑:
请参阅本问题底部的完整答案.
tl;博士回答:Python有静态嵌套的范围.的静态 方面可以与隐变量声明相互作用,产生非显而易见的结果.
(这可能特别令人惊讶,因为语言通常具有动态性质).
我认为我对Python的范围规则有一个很好的处理,但是这个问题让我彻底陷入困境,而且我的google-fu让我失望了(不是我很惊讶 - 看看问题标题;)
我将从一些可以按预期工作的示例开始,但是可以自由地跳到示例4的多汁部分.
例1.
>>> x = 3
>>> class MyClass(object):
... x = x
...
>>> MyClass.x
3
Run Code Online (Sandbox Code Playgroud)
足够简单:在类定义期间,我们能够访问外部(在本例中为全局)范围中定义的变量.
例2.
>>> def mymethod(self):
... return self.x
...
>>> x = 3
>>> class MyClass(object):
... x = x
... mymethod = mymethod
...
>>> MyClass().mymethod()
3
Run Code Online (Sandbox Code Playgroud)
再次(忽略了为什么人们可能想要这样做),这里没有任何意外:我们可以访问外部范围中的函数.
注意:正如Frédéric在下面指出的那样,这个功能似乎不起作用.请参见示例5(及更高版本).
例3.
>>> def myfunc():
... x = 3
... class MyClass(object):
... x = x
... return MyClass
... …Run Code Online (Sandbox Code Playgroud) 这个消息有点长,有很多例子,但我希望它能帮助我和其他人更好地掌握Python 2.7中变量和属性查找的全部故事.
我正在使用PEP 227(http://www.python.org/dev/peps/pep-0227/)的条款来代码块(例如模块,类定义,函数定义等)和变量绑定(例如作为赋值,参数声明,类和函数声明,for循环等)
我使用的术语变量,可以在不点叫名字,并需要与对象名称限定(如obj.x的属性x对象obj的)名称属性.
Python中有三个范围用于所有代码块,但功能如下:
Python中只有四个块用于函数(根据PEP 227):
变量绑定到块并在块中找到它的规则非常简单:
让我知道验证这条规则的例子,并展示许多特殊情况.对于每个例子,我都会给出我的理解.如果我错了,请纠正我.对于最后一个例子,我不明白结果.
例1:
x = "x in module"
class A():
print "A: " + x #x in module
x = "x in class A"
print locals()
class B():
print "B: " + x #x in module
x = "x in class B"
print locals()
def f(self):
print "f: " + x #x in module
self.x = "self.x in f"
print …Run Code Online (Sandbox Code Playgroud)