作用域:变量生效/可访问的范围,超出范围就无法使用该变量。
Python 一共4层作用域,遵循规则:LEGB 规则
一、LEGB 四层作用域(查找顺序)
- L Local 局部作用域:函数内部定义的变量
- E Enclosing 嵌套外层作用域:外层嵌套函数的局部(闭包)
- G Global 全局作用域:
.py文件顶层、函数外定义的变量 - B Built-in 内置作用域:Python自带内置变量/函数(
print、int、sum)
查找顺序:局部 → 外层嵌套 → 全局 → 内置
二、1. 全局作用域 Global
写在所有函数外面,整个文件任意地方都能读取。
# 全局变量num=100deffunc():# 可以读取全局变量print(num)func()print(num)注意:函数内直接修改全局变量会报错
num=100deffunc():num=200# 新建局部变量,不会改全局print(num)func()print(num)# 还是100想要在函数内修改全局变量:global关键字
num=100deffunc():globalnum# 声明使用全局变量num=200func()print(num)# 200三、2. 局部作用域 Local
函数def内部定义的变量,只能在函数内使用,函数外访问报错。
deftest():a=10# 局部变量print(a)test()print(a)# 报错 NameError: name 'a' is not defined四、3. 嵌套函数作用域 Enclosing(闭包)
外层函数变量,在内层子函数可读,直接赋值会生成局部变量;
想要修改外层函数变量用nonlocal。
defouter():x=5# Enclosing 外层变量definner():nonlocalx# 声明使用外层函数变量,不是全局x=10print(x)inner()print(x)outer()不加nonlocal,内层直接x=10只会创建局部x,不影响外层。
五、4. Built-in 内置作用域
Python内置工具,全局可用,优先级最低。
比如print、len、max、int
不要用内置名当变量名,会覆盖内置功能:
print=123print("hello")# 报错,print被你改成数字了六、总结区分 global / nonlocal
| 关键字 | 作用范围 |
|---|---|
global | 修改模块顶层全局变量 |
nonlocal | 修改外层嵌套函数的局部变量,不涉及全局 |
七、简单例题巩固
a=1# Gdefouter():a=2# Edefinner():a=3# Lprint(a)inner()outer()# 输出 3,优先读取局部L