Ask questions in doubt
The day before yesterday colleagues asked me a question, why the script does not call a __init__. The script is as Follows:
1 classA (object):2 def __init__(self, *args, * *kwargs):3 Print "call Init from%s"%self.__class__4 5 def __new__(cls, *args, * *kwargs):6obj = Object.__new__(cls, *args, * *Kwargs)7 Print "call New from%s"%obj.__class__8 returnobj9 Ten one classB (object): a def __init__(self, *args, * *kwargs): - Print "call Init from%s"%self.__class__ - the def __new__(cls, *args, * *kwargs): -obj = Object.__new__(A, *args, * *Kwargs) - Print "call New from%s"%obj.__class__ - returnobj + -b = b ()
In fact, I am also very strange, this script is very strange, the __new__ of Class B returns an instance of A. Only the __new__ method of B is executed, and the __init__ method of a is not executed.
Deep lost
Encounter this problem:
To go into the first look at the compiled Python instructions for the code, see b, the instructions for the __init__ method of b,
For example, to see how the B () method is called, a method test_b is Added. B () Show just two instructions
Load_global
Call_function
View the Python source code to
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);
See here when a little lost, do not know what Tp_call is a thing, not sure by the Typeobject to operate
(this must be reviewed because Tp_call has already made clear where he came From) ***************
Debugging Problem Solving
Finally resorted to, the big recruit to the Python source code to debug, compiles the Python source code on the Linux to add the parameter--with-debug, then executes gdb -ex r --args python test.py ,
After the Call_function,do_call,pyobject_call executes, make a Breakpoint. Saw him running to the
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;
, i'll see the code at this Point. Find out where the notes have been written:
/* If The returned object is not a instance of type,
It won ' t be initialized. */
well, It's clear. Does not produce a instance that is consistent with the class type, it is not initialized. That is called __init__.
The problem is Solved. Also learned the
Ask me how I know to break in that place, because I have read the code, just understand not so Deep.
Python does not execute __init__