Reputation: 3741
I am trying to overload new
and this is my attempt:-
class String(object):
def __new__(cls, *args, **kargs):
print "in __new__"
return super(String, cls).__new__(cls)
def __init__(self):
print "Initiating instance of String"
raise Exception
def __del__(self):
print "Deleting instance of String"
I read at many places that actually __new__
create the instance and __init__
is just to initialize the instance. I am deliberately throwing exception in __init__
to let it fail. Here call to new
returns the instance but init
fails, so I am expecting an instance which won't have any attributes. But result surprised me like anything -
st = String()
in __new__
Initiating instance of String
Traceback (most recent call last):
File "<pyshell#89>", line 1, in <module>
st = String()
File "<pyshell#88>", line 7, in __init__
raise Exception
As expected it failed in __init__
, Next I tried to print newly created instance 'st'
and result surprised me, it deleted instance before printing.
>>> print st
**Deleting instance of String**
Traceback (most recent call last):
File "<pyshell#90>", line 1, in <module>
print st
NameError: name 'st' is not defined
Please help me to understand this strange behavior.
Note - I know when we should overload __new__
and when we shouldn't.
Upvotes: 4
Views: 89
Reputation: 6341
Exception was raised before Python managed to assign the object in memory to the the variable name. Therefore the reference counter of the object in memory is 0, so it got 'garbage collected', and you got name is not defined
exception.
Update for the comment:
Python runs GC when it tries to allocate memory for a new object, if the threshold is filled. In your case it's probably the threshold for generation 0 that was reached, because it's where that new 'failed' String
object should have been. And the event itself that triggered GC was memory allocation to execute print
.
Upvotes: 3