Conditional Inheritance in Python
It happens most of the time that given a condition we need to decide whether a particular class should inherit a class or not, for example given a person, if he/she is eligible for an admission in a university only then they should be a student otherwise they should not be a student.
Let's consider an example, where given a condition, we want a class (say C) to dynamically inherit from either class A or class B. We need to create two different classes C_A and C_B, which inherit from A and B respectively, However if the conditional inheritance is to either inherit or not based on a condition then we can use a different approach as discussed below
Example 1: Conditional Inheritance between 2 classes:
Create two classes C_A and C_B, and based on the condition return the respective class object.
class A(object):
def __init__(self, x):
self.x = x
def getX(self):
return self.X
class B(object):
def __init__(self, x, y):
self.x = x
self.y = y
def getSum(self):
return self.X + self.y
# inherits from A
class C_A(A):
def isA(self):
return True
def isB(self):
return False
# inherits from B
class C_B(B):
def isA(self):
return False
def isB(self):
return True
# return required Object of C based on cond
def getC(cond):
if cond:
return C_A(1)
else:
return C_B(1,2)
# Object of C_A
ca = getC(True)
print(ca.isA())
print(ca.isB())
# Object of C_B
cb = getC(False)
print(cb.isA())
print(cb.isB())
Output:
True False False True
Example 2: For Either inheriting or not from A:
The approach is to use conditional statements while declaring the classes the given class C inherits. The below code executes and returns True
class A(object):
def __init__(self, x):
self.x = x
def getX(self):
return self.X
# Based on condition C inherits
# from A or it inherits from
# object i.e. does not inherit A
cond = True
# inherits from A or B
class C(A if cond else object):
def isA(self):
return True
# Object of C_A
ca = C(1)
print(ca.isA())
Output:
True
Example 3: The following code won't run, as C does not inherit from A, thus has a default constructor that does not take any argument
class A(object):
def __init__(self, x):
self.x = x
def getX(self):
return self.X
# Based on condition C inherits from
# A or it inherits from object i.e.
# does not inherit A
cond = False
## inherits from A or B
class C(A if cond else object):
def isA(self):
return True
# Object of C_A
ca = C(1)
print(ca.isA())
Output:
TypeError Traceback (most recent call last) <ipython-input-16-f0efc5a814d9> in <module> 17 18 # Object of C_A ---> 19 ca = C(1) 20 print(ca.isA()) 21 TypeError: object() takes no parameters