Python没有执行__init__
疑惑 提出问题
前天同事问我一个问题,为什么这个脚本中的没有调用A 的__init__。脚本如下:
class A(object):
def __init__(self, *args, **kwargs):
print "Call init from %s" %self.__class__ def __new__(cls, *args, **kwargs):
obj = object.__new__(cls, *args, **kwargs)
print "Call new from %s" %obj.__class__
return obj class B(object):
def __init__(self, *args, **kwargs):
print "Call init from %s" %self.__class__ def __new__(cls, *args, **kwargs):
obj = object.__new__(A, *args, **kwargs)
print "Call new from %s" %obj.__class__
return obj b = B()
其实我也比较奇怪,这个脚本写的比较奇怪,class B的的__new__返回了A的实例。也只是只执行了B的__new__方法,并没有执行A的__init__方法。
深入 迷失
遇到这个问题:
要深入首先查看了一下代码的编译后的python指令,查看B,是B的__init__方法的指令,
如上图,为了具体查看B()方法是如何调用,就添加了一个方法test_B。B()显示仅仅是两条指令
LOAD_GLOBAL
CALL_FUNCTION
查看Python源代码,到
PyObject_Call(PyObject *func, PyObject *arg, PyObject *kw)
{
ternaryfunc call;
if ((call = func->ob_type->tp_call) != NULL) {
PyObject *result;
if (Py_EnterRecursiveCall(" while calling a Python object"))
return NULL;
result = (*call)(func, arg, kw);
**************看到这里的时候有点迷失了,不知道tp_call是个什么东西了,不确定由typeobject来操作
(这个必须进行检讨因为tp_call已已经明确了他来自哪里)***************
调试 问题解决
最后使出了,大招对Python源代码进行调试,在Linux上编译python源代码加上参数--with-debug, 然后执行gdb -ex r --args python test.py
,
在call_function,do_call,PyObject_Call 执行到之后,打上断点。看到他运行到了
type_call(PyTypeObject *type, PyObject *args, PyObject *kwds)
{
obj = type->tp_new(type, args, kwds);
if (obj != NULL) {
if (!PyType_IsSubtype(obj->ob_type, type))
return obj;
,这个时候我再去看代码。发现哪里已经写好注释了:
/* If the returned object is not an instance of type,
it won't be initialized. */
好吧,很明确了了。没有产生和class类型一致的instance,就不会进行初始化。即调用__init__。
问题解决了。。也学习了
要问我怎么知道在那个地方打断点,因为我已经看过了代码,只是理解没有那么深。
Python没有执行__init__的更多相关文章
- python中的__init__ 、__new__、__call__小结
这篇文章主要介绍了python中的__init__ .__new__.__call__小结,需要的朋友可以参考下 1.__new__(cls, *args, **kwargs) 创建对象时调用,返回 ...
- 从底层理解Python的执行
摘要:是否想在Python解释器的内部晃悠一圈?是不是想实现一个Python代码执行的追踪器?没有基础?不要怕,这篇文章让你初窥Python底层的奥妙. [编者按]下面博文将带你创建一个字节码级别的追 ...
- python 中的__init__.py的用法与个人理解
使用Python模块常见的情况是,事先写好A.py文件,需要import B.py文件时,先拷贝到当前目录,然后再import 这样的做法在程序量较小的情况下是可行的,如果程序交互复杂程度稍高,就很费 ...
- Python中的__init__()和__call__()函数
Python中的__init__()和__call__()函数 在Python的class中有一些函数往往具有特殊的意义.__init__()和__call__()就是class很有用的两类特殊的函数 ...
- 【转】【Python】Python中的__init__.py与模块导入(from import 找不到模块的问题)
python中的Module是比较重要的概念.常见的情况是,事先写好一个.py文 件,在另一个文件中需要import时,将事先写好的.py文件拷贝 到当前目录,或者是在sys.path中增加事先写好的 ...
- python中的__init__(self)是什么意思呢
python中的__init__(self)是什么意思呢 init(self)这个时类的初始化函数 1 2 3 4 class Obj: def init(self): print 1 obj = O ...
- 第8.3节 Python类的__init__方法深入剖析:构造方法与继承详解
第8.3节 Python类的__init__方法深入剖析:构造方法与继承详解 一. 引言 上两节介绍了构造方法的语法及参数,说明了构造方法是Python的类创建实例后首先执行的方法,并说明如果类 ...
- android模拟器(genymotion)+appium+python 框架执行基本原理(目前公司自己写的)
android模拟器(genymotion)+appium+python 框架执行的基本过程: 1.Push.initDate(openid)方法 //业务数据初始化 1.1 v5db.p ...
- python中执行javascript代码
python中执行javascript代码: 1.安装相应的库,我使用的是PyV8 2.import PyV8 ctxt = PyV8.JSContext() ctxt.enter() ...
随机推荐
- 在VirtualBox中安装了Ubuntu后,Ubuntu的屏幕分辨率非常小,操作非常不便。通过安装VirtualBox提供的“增强功能组件”,-摘自网络
在VirtualBox中安装了Ubuntu后,Ubuntu的屏幕分辨率非常小,操作非常不便.通过安装VirtualBox提供的“增强功能组件”,可以解决这一问题,并且使用非常方便. 一.环境 | En ...
- pptp vpn
webalizer是一个高效的.免费的web服务器日志分析程序.其分析结果以HTML文件格式保存,从而可以很方便的通过web服务器进行浏览; http://daliang1215.iteye.com/ ...
- 有关window.location 对象
之前在有关location的使用就一种方式给他的href赋值使页面跳转.今天看项目中的代码看到了一个不一样的用法 window.location.href = 'http://' + document ...
- Altium Designer 多通道设计
转chenzelin2009的csdn博客:http://blog.csdn.net/chenzelin2009/article/details/5751251# Altium Designer的多图 ...
- 以管理员身份启动ClickOnce部署的应用程序
ClickOnce方式部署应用简单方便,估计很多人都用过,但这种方式存在一定的“缺陷”,即以管理员方式启动应用的问题,虽然出于安全考虑可以理解,但给需要管理员权限才能正常运行的程序带来了一定的麻烦,这 ...
- javascript-智能社-JS基础A笔记
JavaScript基础A JavaScript组成 ECMA : 全称ECMAScript,解释器.计算机语言的翻译 DOM:全称Document Object Model,赋予了JS操作HTML的 ...
- 让Windows Server 2008 + IIS 7+ ASP.NET 支持10万并发请求(转)
转自:http://www.cnblogs.com/dudu/archive/2009/11/10/1600062.html 今天下午17点左右,博客园博客站点出现这样的错误信息: Error Sum ...
- Redis与MySQL的结合
Redis与MySQL的结合 目前大部分互联网公司使用MySQL作为数据的主要持久化存储,那么如何让Redis与MySQL很好的结合在一起呢?我们主要使用了一种基于MySQL作为主库,Redis作为高 ...
- SpringMVC + ehcache( ehcache-spring-annotations)基于注解的服务器端数据缓存
背景 声明,如果你不关心java缓存解决方案的全貌,只是急着解决问题,请略过背景部分. 在互联网应用中,由于并发量比传统的企业级应用会高出很多,所以处理大并发的问题就显得尤为重要.在硬件资源一定的情况 ...
- 服务器CPU使用率过高排查与解决思路
发现服务器的cpu使用率特别高 排查思路: -使用top或者mpstat查看cpu的使用情况# mpstat -P ALL 2 1Linux 2.6.32-358.el6.x86_64 (linux— ...