Python中的命名空间,在使用点号 .和不使用点号 .两种情况下使用变量名时,会有不同的处理方式。
赋值语句 var=value
仅仅是创建或改变当前作用域变量名,除非使用了global或者nonlocal关键字
引用语句 var
搜索路径如下:
L(local): 在当前作用域下搜索变量名var
E: 在所有嵌套函数中搜索,从内到外
G(global):在全局作用域中搜索
B(builtins): 在内置作用域中搜索
赋值语句 object.attr=value
在当前命名空间内创建或者修改属性值,不会启用继承搜索树。
引用语句 object.attr
启用继承搜索树,首先在当前实例中搜索属性attr,如果没有找到,就到父类中去搜索(从下至上,从左至右)
示例代码
# !/usr/bin/env python
# -*- coding:utf-8 -*-
# 全局变量(命名空间为当前模块)
var=1
def func_1():
# var引用全局变量
print(var)
def func_2():
# 本地变量(命名空间为当前函数)
var=2
print(var)
class MyClass():
# 类变量(命名空间为当前类)
var=3
def method(self):
# 本地变量(命名空间为当前方法)
var=4
# 实例变量(命名空间为当前实例)
self.var=5
if __name__ == '__main__':
print(var) # 1
func_1() # 1
func_2() # 2
print(var) # 1
myclass=MyClass()
print(myclass.var) # 3
myclass.method()
print(myclass.var) # 5
print(MyClass.var) # 3
global:将被修饰的变量的作用域声明为全局作用域(被声明的变量如果不是已经存在的变量名,会自动创建)。
nonlocal:用于嵌套函数中,将被修饰的变量名的作用域声明为非本地变量(被声明的变量必须是已经存在的变量名,不会自动创建)。
这两个关键字强制改变了属性的作用域,以免引发潜在的问题,不推荐使用,可以用其它手段代替,
例如使用不同的变量名,而不是使用nonlocal声明;直接声明全局变量,而不是在其它作用域中使用global声明。