python __init__ method in inherited class
Solution 1
As far as I know that's not possible, however you can call the init method of the superclass, like this:
class inheritedclass(initialclass):
def __init__(self):
initialclass.__init__(self)
self.attr3 = 'three'
Solution 2
Just call the parent's __init__
using super
:
class inheritedclass(initialclass):
def __new__(self):
self.attr3 = 'three'
super(initialclass, self).__init__()
I strongly advise to follow Python's naming conventions and start a class with a Capital letter, e.g. InheritedClass
and InitialClass
. This helps quickly distinguish classes from methods and variables.
Solution 3
First of all you're mixing __init__
and __new__
, they are different things. __new__
doesn't take instance (self
) as argument, it takes class (cls
).
As for the main part of your question, what you have to do is use super
to invoke superclass' __init__
.
Your code should look like this:
class initialclass(object):
def __init__(self):
self.attr1 = 'one'
self.attr2 = 'two'
class inheritedclass(initialclass):
def __init__(self):
self.attr3 = 'three'
super(inheritedclass, self).__init__()
Solution 4
It's incredibly simple. Define a new __init__
method and call the parent's __init__
at the beginning.
# assuming a class Base, its __init__ takes one parameter x
class Derived(Base):
def __init__(self, x, y):
# whatever initialization is needed so we can say Derived is-a Base
super(Derived, self).__init__(x)
# now, add whatever makes Derived special - do your own initialization
self.y = y
In Python 3, you don't have to (and therefore propably shouldn't, for simplicity) explicitly inherit from object
or pass the class and self
to super
.
Related videos on Youtube
Anake
Updated on December 10, 2020Comments
-
Anake over 3 years
I would like to give a daughter class some extra attributes without having to explicitly call a new method. So is there a way of giving the inherited class an
__init__
type method which does not override the__init__
method of the parent class?I have written the code below purely to illustrate my question (hence the poor naming of attributes etc).
class initialclass(): def __init__(self): self.attr1 = 'one' self.attr2 = 'two' class inheritedclass(initialclass): def __new__(self): self.attr3 = 'three' def somemethod(self): print 'the method' a = inheritedclass() for each in a.__dict__: print each #I would like the output to be: attr1 attr2 attr3
Thank you
-
khachik about 13 yearsCall
initialclass.__init__
in the derived class constructor. However, the order ofattrX
is not guaranteed. -
Admin about 13 yearsDo not override
__new__
unless you know exactly what it does and why you need to fiddle with it. You propably don't know. It's not another name for__init__
. It's three levels more magic than one us usually concerned with, especially beginners. -
Lauritz V. Thaulow about 13 yearsNote that the argument to
__new__
is the class ofself
, notself
, as it's an implicit class method. So in your example you're actually setting the class attributeinheritedclass.attr3
, notself.attr3
as you thought.
-
-
Admin about 13 yearsSpecifically, use
super(DerivingClass, self).__init__()
. Or justsuper().__init__()
in Python 3. Edit: -1 because 1.super
needs the inheriting(!) class and 2. you override__new__
needlessly, and the code as of now is in fact incorrect (it creates a class attributeattr3
). -
Admin about 13 yearsVirtual -1. No need to do any extra work, let alone
hasattr
and extra methods, in the parent class. You can simply define a new__init__
that calls the parent's__init__
usingsuper
. -
Anake about 13 yearsthis works with the new method but as lazyr told me (correctly) that I shouldn't use new, I think the correct answer for me yexo's. Thanks though!
-
Lauritz V. Thaulow about 13 years@delnan I know this, but the question was "is there a way of giving the inherited class an init type method which does not override the init method of the parent class". I've provided such a way. This has the added benefit of giving an entrypoint to calling only the subclass init from some other subclass method.
-
Admin about 13 yearsThat's why it's virtual. I know it's what OP asked for, but OP asked "How do I use a hammer to do this?" and the answer is "You use a screwdriver".
-
Anake about 13 yearsthanks,my mistake about the new method. I am trying to use super and I keep getting this error: TypeError: super() argument 1 must be type, not classobj. (I copied and pasted you code exactly as well)
-
Admin about 13 years@Anake:
initialclass
needs to inheritobject
(class initialclass(object)
), otherwise it's an old-style class, which is little more than a headache-inducing relic from the past and should be avoided. -
Lauritz V. Thaulow about 13 years@delnan What I thought OP asked was, to borrow your anology, "How do I use a hammer to do this when I don't want to use a screwdriver?". I assumed overriding included extending, since to my mind an extended method is simply a type of overridden method -- one that calls the parent method somehow. I assumed, wrongly it seems, he knew how to extend a method. By the way, aren't all python methods virtual? I've never heard anyone talk about virtual methods in python.
-
Admin about 13 yearsYou're correct about Python methods being virtual, the -1 is virtual ;)
-
Lauritz V. Thaulow about 13 years@Anake Credit where credit is due, it was @delnan who told you not to use
__new__
, I just explained what your code actually did. By the way,__new__
must return an instance of its class if you implement it. In the above answer, and in your code too,inheritedclass() is None
! In other words, it doesn't work at all. (I mistakenly gave this answer an upvote, didn't read the code properly, and now I can't change it :(.) -
qwwqwwq over 10 yearsbrilliant, ive been trying to figure out a good way to handle this case for awhile
-
Mohsin Bukhari about 6 yearsare there any downsides to this?