1、内部代码可以访问外部变量,但外部代码无法访问内部变量。
2、python的作用域一共有四层:局部作用域 L (Local)-->>闭包函数外的函数中 E ( Enclosing ) -->> 全局作用域 G ( Global ) -->> 内建作用域 B (Built-in)。记成LEGB。
3、python会按照 L -- E -- G -- B的顺序去查找变量,如果还是找不到就会报变量错误。如下所示,函数func()在局部和闭包函数外都没有找到变量a,但是在全局变量中找到了a,所以可以正常打印值。
注意:python变量作用域取决于其函数代码块在整体代码中的位置,而不是被调用的位置!
上图的例子中,func2()在查找变量a时是直接跳出函数,在全局变量中找,而不是在fun1()中找。即使将func1()和func2()互换位置,原理也是一样的。如果将func2()写成闭包,如下图所示。则输出结果是10,因为此时,func2()查找变量a会从func1()中去找。
4、如果函数体在没有声明情况下,直接对可以查找到的外部变量进行修改会怎么样呢?
python规定,函数内部要修改一个变量,那么这个变量必须是内部变量,或者使用全局变量global进行声明!
5、全局变量 global & 非全局变量nonlocal
(1)global,声明使用全局变量。
如前所述,python寻找变量会按照 L - E - G - B的顺序进行查找,global的作用就是声明使用G层的变量。如4中所述。
(2)如果想要使用E层的变量怎么办呢?可以使用nonlocal 进行声明,如下面的例子。
函数inner使用的是闭包外面的a=2这个变量,如果不进行声明,则inner会自己重新创建一个变量a。
总结起来即:global声明使用全局变量,nonlocal声明使用函数嵌套关系外层的变量,即闭包外部的变量。