|
__new__ v __init__ - python constructor alternatives?
The constructor you'll normally override (and call when you create an object) in Python is called __init__, but there is also a method called __new__ available to the class author.
- If __new__ is defined on a class, it is called in preference to __init__
- With __new__ you return the object you have constructed, whereas with __init__ there is an implicit return of the object in the current class.
Here's a code sample showing three classes with a mixture of different constructors.
class A(object):
def __new__(cls, *args, **kwds):
print "one"
print "A.__new__", args, kwds
return object.__new__(B, *args, **kwds)
def __init__(cls, *args, **kwds):
print "two"
print "A.__init__", args, kwds
class B(object):
def __new__(cls, *args, **kwds):
print "three"
print cls
print B
print "B.__new__", args, kwds
return object.__new__(cls, *args, **kwds)
def __init__(cls, *args, **kwds):
print "four"
print "B.__init__", args, kwds
class C(object):
def __init__(cls, *args, **kwds):
print "five"
print "C.__init__", args, kwds
print C()
print "====================="
print A()
print "====================="
print B()
And here's the result of running that code:
40:~/ndfi grahamellis$ python newvinit
five
C.__init__ () {}
<__main__.C object at 0x6fc10>
=====================
one
A.__new__ () {}
<__main__.B object at 0x6fc10>
=====================
three
<class '__main__.B'>
<class '__main__.B'>
B.__new__ () {}
four
B.__init__ () {}
<__main__.B object at 0x6fc10>
40:~/ndfi grahamellis$
In class C, there's only an __init__ so that's run. Class A has both, and so the __new__ take precedence. In class B, the __new__ takes precendence but it makes an apparent recursive call that's been diverted to __init__ as something of a safeguard - for illustrative purposes, this one!
When would you use __new__?
1. When you want you constructor to return an object of a different type to the class in which it is defined. For example, you have a class "animal" with subclasses "farmanimal" and "pet" and you want the animal cosntructor to be able to examine the data passed in to it and return an animal ... OR a farmanimal OR a pet depending on that data.
2. It has been suggested that experienced base class programmers override __new__ to discourage programmers who subclass them from overwriting their constructors. Personally, I would suggest that a good training course is better than this form of security through obscurity. (written 2007-04-14 07:20:47)
Associated topics are indexed under Y112 - Python - Objects - IntermediateY212 - Further advanced features of Python
Some other Articles
Helsinki - what comes naturallyTurning objects into something you can store - Pickling (Python)Python decorators - wrapping a method call in extra codeA picture (mostly in words) of Helsinki__new__ v __init__ - python constructor alternatives?Using a list of keys and a list of values to make a dictionary in Python - zipPython dictionary for quick look upsA course in HelsinkiPlanters in the SpringA strong team broadens the professional coverage
|
2259 posts, page by page
Link to page ... 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46 at 50 posts per page
This is a page archived from The Horse's Mouth at
http://www.wellho.net/horse/ -
the diary and writings of Graham Ellis.
Every attempt was made to provide current information at the time the
page was written, but things do move forward in our business - new software
releases, price changes, new techniques. Please check back via
our main site for current courses,
prices, versions, etc - any mention of a price in "The Horse's Mouth"
cannot be taken as an offer to supply at that price.
Link to Ezine home page (for reading).
Link to Blogging home page (to add comments).
|
|