R
Ramchandra Apte
Should one always add super().__init__() to the __init__? The reason for this is the possibility of changing base classes (and forgetting to update the __init__).
Should one always add super().__init__() to the __init__? The reason for this is the possibility of changing base classes (and forgetting to update the __init__).
Should one always add super().__init__() to the __init__? The reason for this is the possibility of changing base classes (and forgetting to update the __init__).
Should one always add super().__init__() to the __init__? The reason for
this is the possibility of changing base classes (and forgetting to
update the __init__).
No. Only add code that works and that you need. Arbitrarily adding calls
to the superclasses "just in case" may not work:
py> class Spam(object):
... def __init__(self, x):
... self.x = x
... super(Spam, self).__init__(x)
...
py> x = Spam(1)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 4, in __init__
TypeError: object.__init__() takes no parameters
No. Only add code that works and that you need. Arbitrarily adding calls
to the superclasses "just in case" may not work:
py> class Spam(object):
... def __init__(self, x):
... self.x = x
... super(Spam, self).__init__(x)
...
py> x = Spam(1)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 4, in __init__
TypeError: object.__init__() takes no parameters
Chris Angelico said:That's because you're subclassing something that doesn't take
parameters and giving it parameters. Of course that won't work. The
normal and logical thing to do is to pass on only the parameters that
you know the parent class expects... but that implies knowing the
parent, so it's kinda moot.
No. Only add code that works and that you need. Arbitrarily adding calls
to the superclasses "just in case" may not work:
py> class Spam(object):
... def __init__(self, x):
... self.x = x
... super(Spam, self).__init__(x)
...
py> x = Spam(1)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 4, in __init__
TypeError: object.__init__() takes no parameters
I forgot something:
I meant super().__init__() or similar
That's because you're subclassing something that doesn't take parameters
and giving it parameters. Of course that won't work. The normal and
logical thing to do is to pass on only the parameters that you know the
parent class expects... but that implies knowing the parent, so it's
kinda moot.
It is not necesarily calling the parent class. It calls the initializer
of the next class in the MRO order and what class that is depends on the
actual multiple inheritance structure it is used in, which can depend on
subclasses that you don't know yet. This makes it even worse.
Which is exactly my point -- you can't call the superclass "just in case"
it changes, because you don't know what arguments the new superclass or
classes expect. You have to tailor the arguments to what the parent
expects, and even whether or not you have to call super at all.[1]
super() is not some magic command "don't bother me with the details, just
make method overriding work". You have to actually think about what you
are overriding.
What about it? Please try to remember that we can't read your mind and
don't know what you are thinking, we can only work from what you put in
writing.
There is no difference between super(Class, self).__init__ and
super().__init__ except that the second version only works in Python 3.
I don't quite follow you here. It sounds like you are saying that if you
have these classes:
# pre-existing classes
class A(object): pass
class B(object): pass
# your class
class C(A, B): pass
and somebody subclasses A or B, the MRO of C will change. That is not
actually the case as far as I can see.
When I said "super().__init__()" it could have been "super().__init__(size+67)" or whatever arguments are needed for __init__
[1] You *should* call super, unless you have an excellent reason not to,
so that your class doesn't break multiple-inheritance. But you need to do
so with care making sure that the argument signatures are designed for
cooperative use of super.
The MRO of C will not change, but the class that follows C may be
different in the MRO of a subclass.
I think Piet's (and Ian's) point is, you can't assume thatTo quote a famous line from the movie Cool Hand Luke, "what we have here,
is a failure to communicate."
What do you mean by one class following another? Which class is it
that follows C? What subclass are you talking about, and what is it
subclassing?
Want to reply to this thread or ask your own question?
You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.