深入解析Python中的__builtins__内建对象


Posted in Python onJune 21, 2016

如果你已经学习了包,模块这些知识了。
你会不会有好奇: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 "module name __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
import file1

"""结果:
module name __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__

def open(path):
  f = __builtin__.open(path, 'r')
  return UpperCaser(f)

class UpperCaser:
  __metaclass__ = type

  def __init__(self, f):
    self._f = f

  def read(self):
    return self._f.read().upper()

print open('./a.txt').read()
# 将会全部转为大写输出

Note:Python3.X版本中,内建模块更名为builtins,与Python2.X有所不同

Python 相关文章推荐
python格式化字符串实例总结
Sep 28 Python
python进阶之多线程对同一个全局变量的处理方法
Nov 09 Python
python实现对任意大小图片均匀切割的示例
Dec 05 Python
python实现银联支付和支付宝支付接入
May 07 Python
详解Python字符串切片
May 20 Python
Windows系统Python直接调用C++ DLL的方法
Aug 01 Python
python3 反射的四种基本方法解析
Aug 26 Python
python实现猜数游戏(保存游戏记录)
Jun 22 Python
Python文件夹批处理操作代码实例
Jul 21 Python
python中pathlib模块的基本用法与总结
Aug 17 Python
Python的logging模块基本用法
Dec 24 Python
在Pycharm中安装Pandas库方法(简单易懂)
Feb 20 Python
浅谈Python中函数的参数传递
Jun 21 #Python
对比Python中__getattr__和 __getattribute__获取属性的用法
Jun 21 #Python
常见python正则用法的简单实例
Jun 21 #Python
小议Python中自定义函数的可变参数的使用及注意点
Jun 21 #Python
简单讲解Python编程中namedtuple类的用法
Jun 21 #Python
Python编程中实现迭代器的一些技巧小结
Jun 21 #Python
Centos Python2 升级到Python3的简单实现
Jun 21 #Python
You might like
PHP 存储文本换行实现方法
2010/01/05 PHP
10 个经典PHP函数
2013/10/17 PHP
一个php生成16位随机数的代码(两种方法)
2014/09/16 PHP
PHP的RSA加密解密方法以及开发接口使用
2018/02/11 PHP
CI(CodeIgniter)框架中URL特殊字符处理与SQL注入隐患分析
2019/02/28 PHP
如何运行/调试你的PHP代码
2020/10/23 PHP
JQuery入门—编写一个简单的JQuery应用案例
2013/01/03 Javascript
js 金额格式化来回转换示例
2014/02/23 Javascript
基于NodeJS的前后端分离的思考与实践(四)安全问题解决方案
2014/09/26 NodeJs
Nodejs中调用系统命令、Shell脚本和Python脚本的方法和实例
2015/01/01 NodeJs
javascript事件委托的方式绑定详解
2015/06/10 Javascript
JS实现的表格行鼠标点击高亮效果代码
2015/11/27 Javascript
js计算系统当前日期是星期几的方法
2016/07/14 Javascript
js判断PC端与移动端跳转
2020/12/24 Javascript
vue2 前端搜索实现示例
2018/02/26 Javascript
js捆绑TypeScript声明文件的方法教程
2018/04/13 Javascript
React手稿之 React-Saga的详解
2018/11/12 Javascript
webpack配置proxyTable时pathRewrite无效的解决方法
2018/12/13 Javascript
深入koa-bodyparser原理解析
2019/01/16 Javascript
webpack3升级到webpack4遇到问题总结
2019/09/30 Javascript
Cpy和Python的效率对比
2015/03/20 Python
Python中线程的MQ消息队列实现以及消息队列的优点解析
2016/06/29 Python
Python中文件I/O高效操作处理的技巧分享
2017/02/04 Python
python+matplotlib实现鼠标移动三角形高亮及索引显示
2018/01/15 Python
python 从csv读数据到mysql的实例
2018/06/21 Python
python中os包的用法
2020/06/01 Python
Python爬虫之Selenium设置元素等待的方法
2020/12/04 Python
pytorch下的unsqueeze和squeeze的用法说明
2021/02/06 Python
英国在线花园中心:You Garden
2018/06/03 全球购物
捷克街头、运动和滑板一站式商店:BoardStar.cz
2019/10/06 全球购物
汽车工程专业应届生求职信
2013/10/19 职场文书
酒店应聘自荐信
2013/11/09 职场文书
初三班主任寄语大全
2014/04/04 职场文书
刘公岛导游词
2015/02/05 职场文书
我的1919观后感
2015/06/03 职场文书
解决linux下redis数据库overcommit_memory问题
2022/02/24 Redis