Local 一个函数定义了一个 local 作用域; PyFrameObject 中的 f_local 属性
Global 一个 module 定义了一个 global 作用域; PyFrameObject 中的 f_global 属性.
BuiltIn open, dir 的作用域等等, python 最顶层的作用域
Enclosing
例子,
b = 2
def funcO():
b = 3
def funcI():
print(b)
return funcI f = funcO()
f() # Output,
3 #1 例子的输出结果是 '' 而不是代码块儿最外层所定义的 'b = 2'.
f() 实际调用的内嵌在 funcO 中的 funcI 函数. funcI 位于 funcO 之内, 所以函数 funcI 的作用域内嵌于函数 funcO 的作用域内.
即, 函数 funcO 的作用域是内嵌函数 funcI 的'直接外围作用域', 所以例子的结果是 '' 而不是 ''.
单纯按照代码块儿的结构来说, 在 #1 处 'b = 3' 这个约束已经不再对 'f()' 这个调用起作用, 但是从打印的结果来看显然不是这样(依然起作用).
Python 虚拟机在执行 'f = funcO()' 的时候会执行 'def funcI():' (因为 函数 funcO return 了 funcI 函数对象),
就在这个时候 约束'b = 3' 与函数对象 funcI 捆绑了一起, 并把捆绑后的街哦过返回, 这个捆绑起来的整体被称为 '闭包'('捆绑' 一词可以理解为 '直接外围作用域' 的绑定过程).
闭包是 LEGB 规则中的 E -> enclosing 的首字母, 表示的是 '直接外围作用域' 这个概念. global 关键字,
例子,
c = 1
def func1():
print(c) def func2():
print(c)
c = 3
print(c) func1()
func2() Output,
1 # func1() 的打印
func2() # func2() 的打印
print(c)
UnboundLocalError: local variable 'c' referenced before assignment func1 和 func2 同是对'直接外围作用域'的搜索, 为什么一个正确搜索约束 'c = 1',另一报错呢?
先来了解一个名字的定义 - '最内嵌套作用域规则'.
最内嵌套作用域规则:由一个赋值语句引进的名字在这个赋值语句所在的作用域里是可见(起作用)的,
而且在其内部嵌套的每个作用域里也可见,除非它被嵌套于内部的,
引进同样名字的另一条赋值语句所遮蔽/覆盖。 从 exception 中得知, 变量 c 没有被定义. 上述问题就出现在'定义'的后半句,‘除非’分句 - '除非它被嵌套于内部的,
引进同样名字的另一条赋值语句所遮蔽/覆盖。' 恰巧紧接着报错处, 通过赋值语句引进了一个同名约束('c = 3'),进而破坏了'最内嵌套作用域规则'. 现在尝试修改这个引用错误,
c = 1
def func1():
print(c) # def func2():
global c #2 在引用之前通过 global 关键字指定作用域
print(c) #
c = 3
print(c) # func1()
func2()
print(c) # Output,
1 #
1 #2 python 理解了编程者的意图
3 #
3 #
进一步再看一个闭包的例子,
d = 1
def func2():
d = 3
def func2I():
global d
print(d) #
d += 4 #2 重写直接外层作用域
print(d) #
return func2I abc = func2()
abc()
print(d) # Output,
1 #1 global 关键字 打破 LEGB 规则, 限定引用直接外层作用于
5 #2 直接外层作用于被重写
5 #3 被重写的‘直接外作用域’(代码块儿最外层的 'd = 1' 这个约束)作用于 LEGB 规则下作用域

Python LEGB (Local, Enclosing, Global, Build in) 规则的更多相关文章

  1. TLS 与 python thread local

    TLS 先说TLS( Thread Local Storage),wiki上是这么解释的: Thread-local storage (TLS) is a computer programming m ...

  2. Use Local Or Global Index?

    常常我们须要将大表依据分区键进行分区,当建立索引的时候.我们究竟使用local 还是global 索引呢 先看看两种索引的特点: 本地索引特点: 1. 本地索引一定是分区索引.分区键等同于表的分区键. ...

  3. Python 变量作用域 LEGB (上)—— Local,Global,Builtin

    Python 变量作用域的规则是 LEGB LEGB含义解释:L —— Local(function):函数内的名字空间E —— Enclosing function locals:外部嵌套函数的名字 ...

  4. python 局部local和全局global变量

    global和local变量 虽然简单,但是还是记录一下,主要是转载 转载自:http://blog.sina.com.cn/s/blog_436992740102ux8z.html   先看一段代码 ...

  5. python中的关键字global和nonlocal

    知识点: global将一个变量变为全局变量 nonlocal改变最近的变量,又不是全局作用. 1.global 在python中,当引用一个变量的时候,对这个变量的搜索按找本地作用域(Local). ...

  6. python 局部变量和全局变量 global

    当你在函数定义内声明变量的时候,它们与函数外具有相同名称的其他变量没有任何关系,即变量名称对于函数来说是 局部 的.这称为变量的 作用域 .所有变量的作用域是它们被定义的块,从它们的名称被定义的那点开 ...

  7. Python局部变量和全局变量global

    当你在函数定义声明变量的时候,它们与函数外具有相同名称的其它变量没有任何关系,即变量名称对于函数来说是 局部  的.这称为变量的 作用域 .所有变量的作用域是它们被定义的块,从它们的名称被定义的那点开 ...

  8. python: local variable 'xxx' referenced before assignment

    问题发现 xxx = 23 def PrintFileName(strFileName): if xxx == 23: print strFileName xxx = 24 PrintFileName ...

  9. [Python]threading local 线程局部变量小測试

    概念 有个概念叫做线程局部变量.一般我们对多线程中的全局变量都会加锁处理,这样的变量是共享变量,每一个线程都能够读写变量,为了保持同步我们会做枷锁处理.可是有些变量初始化以后.我们仅仅想让他们在每一个 ...

随机推荐

  1. 原生javascript实现选项卡(基础版)

    一.实现原理 1.主要运用“排他思想”,在设置当前元素前,先把相应元素恢复到默认状态 2.给相应元素添加下标的应用 二.代码展示 <!DOCTYPE html> <html> ...

  2. Windows10内嵌Ubuntu子系统配置python开发环境

    Windows10内嵌Ubuntu子系统配置python开发环境 安装pycharm. 到intellij idea网站下载Linux环境下载免费的pycharm,通过ubuntu子系统内部的/mnt ...

  3. pyton 封装

    定义:在类中将方法和属性隐藏起来 一.私有化 1.格式 __名字,在名字前加双下划线 2.私有化对象 对象属性 静态属性 普通方法 3.作用 1)在类的外面不能直接调用类的方法和属性 2)类的属性值不 ...

  4. [bzoj4815] [洛谷P3700] [Cqoi2017] 小Q的表格

    Description 小Q是个程序员. 作为一个年轻的程序员,小Q总是被老C欺负,老C经常把一些麻烦的任务交给小Q来处理. 每当小Q不知道如何解决时,就只好向你求助.为了完成任务,小Q需要列一个表格 ...

  5. 最强PostMan使用教程

    最近需要测试产品中的REST API,无意中发现了PostMan这个chrome插件,把玩了一下,发现postman秉承了一贯以来google工具强大,易用的特质.独乐乐不如众乐乐,特此共享出来给大伙 ...

  6. Java基础语法和基本数据类型

    Java基础语法 一个Java程序可以认为是一系列对象的集合,而这些对象通过调用彼此的方法来协同工作. 对象:对象是类的一个实例,有状态(属性)和行为(方法). 类:类是一个模板,他描述一类对象的行为 ...

  7. nuxt.js学习初探

    项目目标 把我个人博客的前端界面部分使用nuxt框架进行服务端渲染 nuxt介绍 nuxt可以把spa根据路由将单页面分割成多页面,比起vue的ssr渲染要更容易使用 nuxt的使用 项目创建 npx ...

  8. Mayor's posters (线段树+离散化)

    Mayor's posters Description The citizens of Bytetown, AB, could not stand that the candidates in the ...

  9. AVLtree(C++实现)有统一的旋转操作

    在学习完AVLtree之后,我发现,左旋,右旋均可以采用统一的旋转方式来实现,所以把代码贴在下面 代码是完整的AVLTree实现 C++标准为C++11 在ubuntu 18.04下通过编译和调试 / ...

  10. ubuntu “快捷方式”

    1.创建.Desktop文件 sudo gedit /usr/share/applications/pycharm.desktop 2.建立pycharm.desktop [Desktop Entry ...