为什么sys.modules中有虚拟模块? [英] Why are there dummy modules in sys.modules?

查看:97
本文介绍了为什么sys.modules中有虚拟模块?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

导入标准的logging模块会使用一堆虚拟条目污染sys.modules:

Importing the standard "logging" module pollutes sys.modules with a bunch of dummy entries:

Python 2.5.4 (r254:67916, Dec 23 2008, 15:10:54) [MSC v.1310 32 bit (Intel)] on win32
>>> import sys
>>> import logging
>>> sorted(x for x in sys.modules.keys() if 'log' in x)
['logging', 'logging.atexit', 'logging.cStringIO', 'logging.codecs', 
'logging.os', 'logging.string', 'logging.sys', 'logging.thread', 
'logging.threading', 'logging.time', 'logging.traceback', 'logging.types']

# and perhaps even more surprising:
>>> import traceback
>>> traceback is sys.modules['logging.traceback']
False
>>> sys.modules['logging.traceback'] is None
True

所以导入这个包将额外的名称放入sys.modules中,除了它们不是模块,只引用None。其他模块(例如xml.dom和编码)也有这个问题。为什么?

So importing this package puts extra names into sys.modules, except that they are not modules, just references to None. Other modules (e.g. xml.dom and encodings) have this issue as well. Why?

编辑:根据bobince的回答,有一些描述原点(参见sys.modules中的虚拟条目一节)和 future of the feature。

Building on bobince's answer, there are pages describing the origin (see section "Dummy Entries in sys.modules") and future of the feature.

推荐答案

sys.modules 中的值是相对查找的缓存失败。

None values in sys.modules are cached failures of relative lookups.

所以当你在包 foo 并且你 import sys ,Python首先查找 foo.sys 模块,如果失败则返回顶级 sys 模块。为了避免在进一步的相对导入上再次检查 foo / sys.py 的文件系统,它会在中存储 sys.modules 标记该模块不存在,后续导入不应该再看,但直接进入加载的 sys

So when you're in package foo and you import sys, Python looks first for a foo.sys module, and if that fails goes to the top-level sys module. To avoid having to check the filesystem for foo/sys.py again on further relative imports, it stores None in the sys.modules to flag that the module didn't exist and a subsequent import shouldn't look there again, but go straight to the loaded sys.

这是一个你无法有效依赖的cPython实现细节,但是如果你做了讨厌的魔法,你需要知道它导入/重新加载黑客。

This is a cPython implementation detail you can't usefully rely on, but you will need to know it if you're doing nasty magic import/reload hacking.

它适用于所有软件包,而不仅仅是日志记录。例如, import xml.dom 并在尝试导入时在模块列表中查看 xml.dom.xml code> xml 来自 xml.dom

It happens to all packages, not just logging. For example, import xml.dom and see xml.dom.xml in the module list as it tries to import xml from inside xml.dom.

随着Python移动对于绝对进口而言,这种丑陋感会更少。

As Python moves towards absolute import this ugliness will happen less.

这篇关于为什么sys.modules中有虚拟模块?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆