In Python how to call Parent class function as if I were Parent object
Question:
I have a Parent and a Child class, both should execute their own fct in init but Child have to execute first the Parent fct :
class Parent(object):
def __init__(self):
self.fct()
def fct(self):
# do some basic stuff
class Child(Parent):
def __init__(self):
super().__init__()
self.fct()
def fct(self):
# add other stuff
Problem is that super().init() calls the Child fct and not the Parent one as I would like. Of course I could rename Child function as fct2 but I was wondering if I can do what I want to do without changing names (because fct and fct2 do the same thing conceptually speaking, they just apply on different things). It would be nice if I could call super().__init() as if were Parent object.
Answers:
The idea of subclassining is this: if you ever need to use a method to the parent class, just do not create it in the child class.
Otherwise, in a hierarchy with complicated classes and mixins, and you really need the methods to have the same name, there is the name mangling mechanism, triggered by Python when using two underlines __
as a method or attribute prefix:
class Parent(object):
def __init__(self):
self.__fct()
def __fct(self):
# do some basic stuff
class Child(Parent):
def __init__(self):
super().__init__()
self.__fct()
def __fct(self):
# add other stuff
Using the __
prefix makes Python change the name of this method, both in declaration and where it is used when the class is created (at the time the class
statement with its block is itself executed) – and both methods work as if they were named differently, each one only accessible, in an ordinary way, from code in its own class.
Some documentation, mainly older docs, will sometimes refer to this as the mechanism in Python to create "private methods". It is not the samething, although it can serve the same purpose in some use cases (like this). The __fct
method above will be renamed respectively to Parent._Parent__fct
and Child._Child__fct
when the code is executed.
second way, without name mangling:
Without resorting to this name mangling mechanism, it is possible to retrieve attributes from the class where a piece of code is declared by using the __class__
special name (not self.__class__
, just __class__
) – it is part of the same mechanism Python uses to make argumentless super()
work:
class Parent(object):
def __init__(self):
__class__.fct(self) # <- retrieved from the current class (Parent)
def fct(self):
# do some basic stuff
class Child(Parent):
def __init__(self):
super().__init__()
__class__.fct(self)
def fct(self):
# add other stuff
This will also work – just note that as the methods are retrieved from the class object, not from an instance, the instance have to be explicitly passed as an argument when calling the methods.
The name __class__
is inserted automatically in any methods that use it, and will always refer to the class that has the body were it appears – the class itself will be created "in the future", when all the class body is processed and the class
command itself is resolved.
I think you want to run the fct of the parent before running the fct of the child, if so then this is the code:
class Parent:
def __init__(self, obj: object):
self.obj = obj
self.fct()
def fct(self):
# do some basic stuff
class Child:
def __init__(self, par: Parent):
self.par = par
self.fct()
def fct(self):
self.par.fct()
# add other stuff
I have a Parent and a Child class, both should execute their own fct in init but Child have to execute first the Parent fct :
class Parent(object):
def __init__(self):
self.fct()
def fct(self):
# do some basic stuff
class Child(Parent):
def __init__(self):
super().__init__()
self.fct()
def fct(self):
# add other stuff
Problem is that super().init() calls the Child fct and not the Parent one as I would like. Of course I could rename Child function as fct2 but I was wondering if I can do what I want to do without changing names (because fct and fct2 do the same thing conceptually speaking, they just apply on different things). It would be nice if I could call super().__init() as if were Parent object.
The idea of subclassining is this: if you ever need to use a method to the parent class, just do not create it in the child class.
Otherwise, in a hierarchy with complicated classes and mixins, and you really need the methods to have the same name, there is the name mangling mechanism, triggered by Python when using two underlines __
as a method or attribute prefix:
class Parent(object):
def __init__(self):
self.__fct()
def __fct(self):
# do some basic stuff
class Child(Parent):
def __init__(self):
super().__init__()
self.__fct()
def __fct(self):
# add other stuff
Using the __
prefix makes Python change the name of this method, both in declaration and where it is used when the class is created (at the time the class
statement with its block is itself executed) – and both methods work as if they were named differently, each one only accessible, in an ordinary way, from code in its own class.
Some documentation, mainly older docs, will sometimes refer to this as the mechanism in Python to create "private methods". It is not the samething, although it can serve the same purpose in some use cases (like this). The __fct
method above will be renamed respectively to Parent._Parent__fct
and Child._Child__fct
when the code is executed.
second way, without name mangling:
Without resorting to this name mangling mechanism, it is possible to retrieve attributes from the class where a piece of code is declared by using the __class__
special name (not self.__class__
, just __class__
) – it is part of the same mechanism Python uses to make argumentless super()
work:
class Parent(object):
def __init__(self):
__class__.fct(self) # <- retrieved from the current class (Parent)
def fct(self):
# do some basic stuff
class Child(Parent):
def __init__(self):
super().__init__()
__class__.fct(self)
def fct(self):
# add other stuff
This will also work – just note that as the methods are retrieved from the class object, not from an instance, the instance have to be explicitly passed as an argument when calling the methods.
The name __class__
is inserted automatically in any methods that use it, and will always refer to the class that has the body were it appears – the class itself will be created "in the future", when all the class body is processed and the class
command itself is resolved.
I think you want to run the fct of the parent before running the fct of the child, if so then this is the code:
class Parent:
def __init__(self, obj: object):
self.obj = obj
self.fct()
def fct(self):
# do some basic stuff
class Child:
def __init__(self, par: Parent):
self.par = par
self.fct()
def fct(self):
self.par.fct()
# add other stuff