深入解析Python中的__builtins__内建对象
如果你已经学习了包,模块这些知识了。
你会不会有好奇:Python为什么可以直接使用一些内建函数,不用显式的导入它们,比如str()int()dir()...?
原因是Python解释器第一次启动的时候__builtins__就已经在命名空间了(Note:有s)
进Shell看看:
>>>globals() {'__builtins__':<module'__builtin__'(built-in)>, '__name__':'__main__','__doc__':None,'__package__':None}
你可以再次导入__builtin__(Note:没有s):
import__builtin__ >>>globals() {'__builtins__':<module'__builtin__'(built-in)>, '__name__':'__main__','__doc__':None,'__builtin__': <module'__builtin__'(built-in)>,'__package__':None}
这时候多了一个__builtin__对象,你可以判断它们是不是相同的:
>>>__builtin__is__builtins__ True >>>type(__builtin__) <type'module'> >>>type(__builtins__) <type'module'>
现在我们把它从一个文件导入:
#file1.py import__builtin__ print"modulename__name__:",__name__ print"__builtin__is__builtins__:",__builtin__is__builtins__ print"type(__builtin__):",type(__builtin__) print"type(__builtins__):",type(__builtins__) print"__builtins__is__builtin__.__dict__",__builtins__is__builtin__.__dict__ #file2.py importfile1 """结果: modulename__name__:file __builtin__is__builtins__:False type(__builtin__):<type'module'> type(__builtins__):<type'dict'> __builtins__is__builtin__.__dict__True """
结论:
__builtins__是对内建模块 __builtin__的引用,并且有如下两个方面差异:
在主模块中,即没有被其他文件导入。__builtins__是对__builtin__本身的引用,两者是相同的。
通过__builtins__is__builtin__.__dict__猜想:
在非'__main__'模块中,也就是模块被导入后,__builtins__应该属于__builtin__.__dict__的一部分,是对__builtin__.__dict__的引用,而非builtin本身,它在任何地方都可见,此时builtins的类型是字典。
装饰内建函数
Python官方文档解释了如何装饰一个内建函数:
import__builtin__ defopen(path): f=__builtin__.open(path,'r') returnUpperCaser(f) classUpperCaser: __metaclass__=type def__init__(self,f): self._f=f defread(self): returnself._f.read().upper() printopen('./a.txt').read() #将会全部转为大写输出
Note:Python3.X版本中,内建模块更名为builtins,与Python2.X有所不同