当前位置: 首页 > article >正文

名称空间(namespaces)与作用域

引入

在python解释器中运行一行代码import this就可以看到“传说”中的python之禅,它体现了使用python进行开发的规范,而最后一句 - Namespaces are one honking great idea -- let's do more of those!就是本文的主角。

名称空间(Namespaces)

名称空间就是存放名字与对象绑定关系的地方,是对栈区的划分。定义一个变量。name = 'python',解释器会申请内存空间存放值'python',将名字name与'python'的内存地址的绑定关系存在栈区中。

有了名称空间之后就可以在栈区中存放相同的名字,在程序执行期间最多会存在三种名称空间,每种名称空间相互独立。

内置名称空间(built-in)

存放的是python解释器内置的名字,比如python中的保留字(关键字)。python解释器启动时内置名称空间就会产生,python解释器关闭,则销毁。

# 在交互式的解释器环境中输入print然后回车
>>> print
<built-in function print>

全局名称空间

只要不是函数内定义也不是内置的名字,剩下的全部都是全局名称。全局名称空间在运行python文件时产生,python文件执行完成之后销毁。

x = 1  # x是全局名称
def func():  # func是全局名称
    print(x)  # print是内置名称

局部名称空间

函数内定义的名字都会被存放在局部名称空间。局部名称空间在调用函数时产生,函数运行完毕后销毁。

def func():  # func全局名称
    x = 100  # x局部名称
    print(x)  # print内置名称 

名称空间与作用域

名称空间的加载顺序是:内置名称空间->全局名称空间->局部名称空间。

名称空间销毁顺序是:局部名称空间->全局名称空间->内置名称空间。

按照名称空间中名字的作用范围可以将三种名称空间划分为两个区域。

全局作用域---全局名称空间、内置名称空间中的名字属于全局作用域,全局作用域中的名字在整个文件执行过程中都不会被销毁,在任意位置都可以使用。

局部作用域---位于局部名称空间中的名字属于局部作用域,局部作用域中的名字在函数调用时产生,调用结束时销毁,只能在函数内使用。

作用域与名字查找优先级

名字顺序的查找需要记住一条准则:名字的查找顺序以函数阶段为准,与调用阶段没有关系。

  • 从局部作用域开始

在局部作用域查找名字,起始位置是局部作用域,现在局部名称空间中查找,找不到再去全局作用域查找,先查找全局名称空间,找不到再去内置名称空间,最后都找不到会抛出异常。

  • 从全局作用域开始

在全局作用域查找名字时,起始位置就是全局作用域,先查找全局名称空间,找不到再去内置名称空间,最后都找不到会抛出异常。

  • 名称空间的“嵌套关系”

这里的嵌套可以理解为不同的名称空间都存在同样的变量名,注意:一定要以函数定义阶段为准,并且牢记名称空间的查找顺序。

global & nonlocal

如果想要在函数内修改全局名称空间中名字的值并且该值是不可变数据类型,需要用到global关键字,如果该值是可变数据类型,则无需使用global,可以直接对原值进行修改。

x = 100
l = [1, 2]
def func():
    global x  # 声明x是全局名称空间的名字
    x = 101
    l.append(3)
func()
print(x)  # 101
print(l)  # [1, 2, 3]

对于嵌套多层的函数,可以使用nonlocal关键字对外层嵌套函数定义的名字进行声明并修改其值。nonlocal会从当前函数的外层函数一层一层去查找声明的名字,如果在最外层函数的名称空间中找不到该名字,会抛出异常。

def func():
    x = 10
    def func1():
        nonlocal x  
        x = 11
    func1()  # 修改func作用域中x的值
    print(x)  # 在func作用域中查看x的值
func()  # 11

http://www.kler.cn/news/18534.html

相关文章:

  • [LeetCode周赛复盘] 第 344 场周赛20230507
  • 从不同视角来看待API数据接口
  • Unity用脚本获取物体和组件(下)
  • MySQL基础(三)基本的SELECT语句
  • eSIM证书要求-证书验证-EID
  • 第1章 Nginx简介
  • 187页9万字企业大数据治理与云平台实施方案(word)
  • sentinel 随笔 0-责任链
  • 俩小伙一晚上写了个 AI 应用,月入两万??(文末附开发教程)
  • Scrum敏捷开发工具-单团队敏捷开发管理
  • Linux用户空间与内核空间通信(Netlink通信机制)
  • 三种方法教你让模糊照片秒变高清图
  • 软件工程开发文档写作教程(05)—可行性研究报告写作规范
  • PBDB Data Service:Ecological and taphonomic vocabulary(生态学和埋葬学术语)
  • Ansys Lumerical | CMOS - 光学仿真方法
  • 一场面试下来,狂飙 Framework底层原理
  • 单链表OJ题:LeetCode--206.反转链表
  • Java之多线程初阶2
  • 【操作系统OS】学习笔记第三章 内存管理【哈工大李治军老师】
  • 数字化战略,如何解读企业财务报表
  • vue 水印组件
  • 【计算机图形学基础教程】MFC基本绘图函数2
  • selenium——unittest框架
  • 基于 EKS Fargate 搭建微服务性能分析系统
  • mysql数据迁移与同步常用解决方案总结
  • python实现异步过程asyncio
  • 【系分论文】论信息系统开发方法及应用
  • VMware集群不可访问 证书到期
  • TCP三次握手
  • 通过实现MyBatis的Interceptor接口在SQL头部增加统一注释