Question

When should the following code be used in Python (Assume that Baseclass inherits from Parent class and Parent class has some variables initiated in __init__() method)

class Baseclass(Parent):
    def __init__(self, some_arg):
        self.some_arg = some_arg
        super(Baseclass, self).__init__()

Does this code makes all the local variables defined in __init__ method of Parent class accessible in Baseclass? What significance does it make?

Was it helpful?

Solution

super keeps your code from being repetitive; a complex __init__ needn't be c/p'ed into your inheriting classes. It also makes MRO work as it should, such that if you use multiple inheritance it will work correctly.

One reason to do this would be to ensure that all of your inheriting objects have certain attributes which they don't have from the parent. If you simply write a new __init__, they won't have them unless you repeat your code. For example:

>>> class A(object):
...     def __init__(self, x):
...             self.x = x
... 
>>> class B(A):
...     def __init__(self, y):
...             self.y = y
... 
>>> Stick = B(15)
>>> Stick.x
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'B' object has no attribute 'x'
>>>

Without calling super during the __init__ the entire method is simply overridden. A call to super here ensures that both variables exist in the inherited class.

>>> class C(A):
...     def __init__(self, x, y):
...             super(C, self).__init__(x)
...             self.y = y
... 
>>> Dave = C(15, 22)
>>> Dave.x
15
>>> Dave.y
22
>>>  

Note that in the super call, x is passed to the __init__() call, but self is taken care of in the super(C, self) part of the code.

EDIT: TyrantWave also rightly points out that super is also quite useful outside of __init__. Take an object with a simple foo method for example.

class Parent(object):
    def foo(self):
        return "I say foo!"

The inherited class may want to just alter the output of this function instead of totally rewriting it. So instead of repeating ourselves and writing the same code over again, we just call super to get the parent's return value, then work with the data and return the child class's modified results.

class Child(Parent):
    def foo(self):
        parent_result = super(Child, self).foo()
        return "I'm a child!! %s" % parent_result

In the above, the call to super returns the Parents value for foo() and then the Child goes on to work with the data further before returning it themselves.

>>> Alan = Parent()
>>> Stan = Child()
>>> Alan.foo()
'I say foo!'
>>> Stan.foo()
"I'm a child!! I say foo!"
>>> 
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top