网易首页 > 网易号 > 正文 申请入驻

Python:模块 __dict__ 详解

0
分享至

在 Python 中,模块(module)是一级命名空间对象。无论是通过 import 加载的标准库模块、第三方模块,还是直接运行的脚本本身,每个模块都以对象形式存在于内存中,并通过其 __dict__ 属性统一管理所有模块级名称。

理解模块的 __dict__,不仅是掌握模块工作机制的关键,也是深入理解 Python 命名空间模型、导入机制以及运行期动态行为的重要基础。

一、模块对象与模块命名空间

(1)模块是运行期对象,而非静态概念

在 Python 中,模块不是“代码文件”的抽象概念,而是运行期存在的实际对象。

print(type(math))    #

每一个模块对象都拥有一组标准属性,例如:

• __name__:模块名称

• __file__:模块源文件路径

• __spec__:模块的导入规范

• __loader__:模块加载器

• __dict__:模块命名空间

其中,__dict__ 是模块命名空间的唯一物理载体,存储了模块中的所有名称。

(2)模块 __dict__ 的定义

模块 __dict__ 表示模块级的命名空间本身。模块中通过赋值语句、函数定义、类定义、import 语句创建的所有名称,最终都存储在这个字典中。

示例:

    pass

加载后查看其命名空间:

print(demo.__dict__.keys())

输出:

dict_keys(['__name__', '__doc__', '__package__', '__loader__', '__spec__', '__file__', '__cached__', '__builtins__', 'x', 'f', 'C'])

可以看到,模块 __dict__ 既包含用户定义的变量、函数、类,也包含系统自动添加的元信息。

二、types 模块与 ModuleType 的作用

为了准确理解模块 __dict__,需要明确模块对象的具体类型。

(1)types 模块的角色

标准库 模块提供了对解释器内部核心对象类型的标准化引用,如:

• FunctionType 函数类型

• MethodType 方法类型

• ModuleType 模块类型

• GeneratorType 生成器类型

这些不是“新类型”,而是对既有内置类型的正式命名,便于类型检查和明确意图。

(2)ModuleType 的本质

types.ModuleType 表示模块对象的类型:

print(type(math) is types.ModuleType)    # True

所有通过 import 得到的模块对象,本质上都是 ModuleType 的实例。

(3)ModuleType 的构造语义

types.ModuleType(name, doc=None)

参数含义:

• name:模块名(对应 __name__)

• doc: 模块文档字符串(对应 __doc__)

示例:

print(m.__dict__)   # {}

(4)ModuleType 创建的是真实模块对象

需要明确的一点是,types.ModuleType 创建的并不是“伪模块”,而是真正的模块对象。区别仅在于:

特性

import 创建的模块

ModuleType 创建的模块

代码执行

自动执行模块代码

不自动执行代码

__dict__ 填充

自动填充

初始为空字典

系统属性

自动设置 __spec__、__loader__

需手动设置

注册到 sys.modules

自动注册

不自动注册

在对象模型层面,它们完全一致:

print(type(m1) is type(m2))  # True

(5)使用 ModuleType 的意义

使用 ModuleType 的目的在于:隔离模块对象结构本身与 import 机制的副作用。

示例:

print(m.__dict__)  # {'x': 42, 'hello': at ...>}

这清晰地体现了:

• 模块属性 ≡ 模块 .__dict__ 中的键值对

• 模块命名空间完全由模块 __dict__ 管理

三、模块 __dict__ 的生命周期

模块 __dict__ 的生命周期与模块对象本身严格一致。

(1)创建阶段

执行顺序为:

1、创建模块对象:实例化 ModuleType

2、初始化空 __dict__:创建空字典作为命名空间

3、执行模块代码:逐条执行语句,将结果写入 __dict__。

exec(open('demo.py').read(), demo.__dict__)    # 导入过程的“概念性等价描述”

(2)运行阶段:动态可变

模块 __dict__ 是一个完全可写的普通字典,可在运行时动态改变:

del demo.__dict__['new_var']

模块在运行期可以:

• 动态添加属性/删除属性

• 可被反射、注入、修改

• 作为插件系统的载体

(3)销毁阶段

当模块对象被垃圾回收时,模块 __dict__ 随对象一同销毁,其命名空间不再存在。

通常,模块会常驻内存,因为 sys.modules 持有对模块对象的强引用。除非显式从 sys.modules 中删除,否则模块对象及其 __dict__ 会一直存在。

四、模块 __dict__ 与属性访问机制

模块属性访问遵循简单直接的规则:

module.attr

在属性存在的情况下,在语义上等价于:

module.__dict__['attr']

二者在异常类型上略有差异。

属性访问特点:

• 无方法绑定:模块中的函数始终是普通函数对象。

• 无 MRO 查找:不存在继承链查找。

• 无描述符处理:不涉及 __get__/__set__ 协议,即使模块中存在实现了描述符协议的对象,模块属性访问也不会触发描述符绑定逻辑。

• 直接字典查找:属性访问就是字典键查找。

示例:

demo.f()  # 返回 "function",不会生成方法对象

五、模块 __dict__ 的典型用途

(1)反射与调试

可用于枚举模块成员、动态分析模块结构以及 REPL / 调试器实现。

pdb.set_trace()  # 调试器内部使用 __dict__ 访问局部变量

(2)动态注入 API

常见于插件系统、框架自动注册以及运行期扩展接口。

    sys.modules[module_name] = module

(3)框架自动注册

    return decorator

六、不同对象的命名空间对比

对象类型

__dict__ 特性

可变性

特殊行为

实例

普通 dict

完全可变

支持属性访问协议

mappingproxy

需通过赋值语句

支持继承、描述符

模块

普通 dict(完全可写)

完全可变

直接字典映射

模块是唯一一个顶层、全局、完全可变的命名空间对象,这也是它常被用作配置容器、插件载体、全局状态管理的原因。

小结

模块 __dict__ 是模块命名空间的实体载体,保存了模块中定义的全部名称。模块对象本质上是 types.ModuleType 的实例,其 __dict__ 是一个普通、完全可写的字典。模块加载时,解释器创建模块对象并逐步填充其 __dict__;运行期中,该字典可被动态修改。模块属性访问直接映射到 __dict__ 查找,不涉及方法绑定或 MRO。

理解模块 __dict__,是理解 Python 命名空间、import 机制以及动态特性的关键基础。


点赞有美意,赞赏是鼓励

特别声明:以上内容(如有图片或视频亦包括在内)为自媒体平台“网易号”用户上传并发布,本平台仅提供信息存储服务。

Notice: The content above (including the pictures and videos if any) is uploaded and posted by a user of NetEase Hao, which is a social media platform and only provides information storage services.

相关推荐
热点推荐
不愧是今年春晚最美的节目,女神们真的美爆啦!

不愧是今年春晚最美的节目,女神们真的美爆啦!

陈列共和
2026-02-18 19:43:08
欧协附加赛1-1大冷门:英超球队遭弱旅逼平,无缘占得先机

欧协附加赛1-1大冷门:英超球队遭弱旅逼平,无缘占得先机

侧身凌空斩
2026-02-20 03:41:28
黄渤大年初二陪老婆回娘家!请岳父母吃海鲜大餐,妻子换新发型美

黄渤大年初二陪老婆回娘家!请岳父母吃海鲜大餐,妻子换新发型美

情感大头说说
2026-02-19 17:49:17
签约已达成,凯尔特人队与刚刚离开快船队的资深后卫重聚

签约已达成,凯尔特人队与刚刚离开快船队的资深后卫重聚

好火子
2026-02-20 01:33:10
为了得到维尼休斯的垂青,巴西各路名媛究竟付出了多大的代价?

为了得到维尼休斯的垂青,巴西各路名媛究竟付出了多大的代价?

罗氏八卦
2026-02-19 18:00:03
南方大米产量第一,为啥超市里大部分还是东北米?南方米去哪了?

南方大米产量第一,为啥超市里大部分还是东北米?南方米去哪了?

天下十三洲猎奇
2026-02-18 23:53:55
翻车!春晚“真弹幕”骗局?骂春晚发不出,夸的秒显,网友当傻子

翻车!春晚“真弹幕”骗局?骂春晚发不出,夸的秒显,网友当傻子

戗词夺理
2026-02-18 17:43:36
女子冰壶:中国6-9负于日本,2胜7负结束本届冬奥会征程

女子冰壶:中国6-9负于日本,2胜7负结束本届冬奥会征程

懂球帝
2026-02-20 00:45:04
宝玉和袭人同房多次,为何一直都没怀孕?黛玉一句调侃道出真相

宝玉和袭人同房多次,为何一直都没怀孕?黛玉一句调侃道出真相

谈史论天地
2026-02-06 17:30:03
索汉蓝橙发色亮相尼克斯!透露选择纽约原因 将接受布朗长期考察

索汉蓝橙发色亮相尼克斯!透露选择纽约原因 将接受布朗长期考察

罗说NBA
2026-02-20 06:59:25
夸美国空气香甜的杨舒平,已被美驱逐出境,如今回国下场怎么样了

夸美国空气香甜的杨舒平,已被美驱逐出境,如今回国下场怎么样了

谈史论天地
2026-02-07 13:20:03
不可思议!大明星年夜饭竟出现外卖盒,网友:有没有可能全是外卖

不可思议!大明星年夜饭竟出现外卖盒,网友:有没有可能全是外卖

火山詩话
2026-02-18 20:45:41
就在今天!2月20日凌晨,WTT大满贯男单爆大冷 世界亚军1:3被淘汰

就在今天!2月20日凌晨,WTT大满贯男单爆大冷 世界亚军1:3被淘汰

皮皮观天下
2026-02-20 05:01:05
孩子越大,越要告诉他这五句人生真相:比成绩更重要的,是活好这一生

孩子越大,越要告诉他这五句人生真相:比成绩更重要的,是活好这一生

青苹果sht
2026-02-20 05:52:21
动手了!张一鸣,自己造芯片

动手了!张一鸣,自己造芯片

首席品牌评论
2026-02-18 14:19:08
突破性进展!微软研发出万年存储玻璃:单块可存4.84TB

突破性进展!微软研发出万年存储玻璃:单块可存4.84TB

快科技
2026-02-19 15:30:06
印度首富的小儿子:减200多斤又变胖,妻子是高种姓出身的白富美

印度首富的小儿子:减200多斤又变胖,妻子是高种姓出身的白富美

小书生吃瓜
2026-01-20 17:26:45
固态电池 比亚迪仰望U9全固态版2026年1月青海首测 技术盈利双突破

固态电池 比亚迪仰望U9全固态版2026年1月青海首测 技术盈利双突破

趣味萌宠的日常
2026-02-20 02:14:34
霍去病早逝之谜的真相:他若不死,汉武帝掏空整个国家也不够赏他

霍去病早逝之谜的真相:他若不死,汉武帝掏空整个国家也不够赏他

史之韵
2026-02-04 00:12:08
为了“掏空”老百姓家底,而编造出来的“4大谎言”,谁信谁倒霉

为了“掏空”老百姓家底,而编造出来的“4大谎言”,谁信谁倒霉

平说财经
2026-02-18 08:38:03
2026-02-20 09:15:00
MediaTea
MediaTea
专业的数字媒体、新媒体技术
1760文章数 76关注度
往期回顾 全部

科技要闻

怒烧45亿,腾讯字节阿里决战春节

头条要闻

专家:美国何时对伊朗动武 三大细节值得关注

头条要闻

专家:美国何时对伊朗动武 三大细节值得关注

体育要闻

宁忠岩4年从第7到摘金,刷新奥运纪录

娱乐要闻

霍启山恋情再添实锤 和娜然同游意大利

财经要闻

面条火腿香菇酱!上市公司这些年请你吃

汽车要闻

量产甲醇插混 吉利银河星耀6甲醇插混版申报图

态度原创

教育
时尚
本地
旅游
健康

教育要闻

彻底弄懂数学本质!空间形式与数量关系解析

冬季羽绒服是最“受捧”的单品,这样选款和搭配,舒适耐看

本地新闻

春花齐放2026:《骏马奔腾迎新岁》

旅游要闻

杭州:西湖宋韵迎新岁

转头就晕的耳石症,能开车上班吗?

无障碍浏览 进入关怀版