Python Inheritance
Python Inheritance
Inheritance is a fundamental concept in object-oriented programming (OOP) that allows one class (the child class) to inherit the attributes and methods from another class (the parent class). This enables code reuse, where the child class can leverage functionality from the parent class and can also define additional behavior or override inherited methods.
1. Basic Inheritance Syntax
To implement inheritance in Python, you define a class that inherits from another class by specifying the parent class in parentheses.
Syntax:
class ChildClass(ParentClass):
# Child class code
The ChildClass inherits all the attributes and methods of the ParentClass.
2. Example of Inheritance
Here’s a basic example where the Dog class inherits from the Animal class.
Example:
# Parent Class
class Animal:
def __init__(self, name):
self.name = name
def speak(self):
print(f"{self.name} makes a sound")
# Child Class inheriting from Animal
class Dog(Animal):
def __init__(self, name, breed):
super().__init__(name) # Call the parent class constructor
self.breed = breed
def speak(self):
print(f"{self.name} barks!")
# Create an object of the Dog class
dog = Dog("Buddy", "Golden Retriever")
dog.speak() # Output: Buddy barks!
In this example:
- The
Dogclass inherits from theAnimalclass. - The
super()function is used in theDogclass constructor to call the parent class (Animal) constructor, initializing thenameattribute. - The
speakmethod is overridden in theDogclass to provide specific behavior for dogs.
3. Using super() in Inheritance
The super() function is used to call methods from the parent class, particularly the constructor (__init__) or other methods that you want to reuse in the child class.
Example with super():
class Animal:
def __init__(self, name):
self.name = name
def speak(self):
print(f"{self.name} makes a sound")
class Dog(Animal):
def __init__(self, name, breed):
super().__init__(name) # Call the parent class constructor
self.breed = breed
def speak(self):
super().speak() # Call the parent class speak method
print(f"{self.name} barks!")
dog = Dog("Max", "Bulldog")
dog.speak() # Output: Max makes a sound
# Max barks!
In this example:
super().__init__(name)is used to call the parent class (Animal) constructor.super().speak()is used to call thespeak()method of the parent class, followed by adding behavior specific toDog.
4. Overriding Methods
A child class can override methods of the parent class to modify or extend the functionality. If the child class provides its own implementation of a method, the parent class’s version is no longer used.
Example:
class Animal:
def speak(self):
print("Animal makes a sound")
class Dog(Animal):
def speak(self):
print("Dog barks")
# Create objects
animal = Animal()
dog = Dog()
animal.speak() # Output: Animal makes a sound
dog.speak() # Output: Dog barks
In this example, the speak method is overridden in the Dog class to provide a specific implementation for dogs.
5. Inheritance Hierarchy
A child class can also inherit from another child class, forming a multi-level inheritance hierarchy.
Example of Multi-level Inheritance:
class Animal:
def __init__(self, name):
self.name = name
def speak(self):
print(f"{self.name} makes a sound")
class Dog(Animal):
def __init__(self, name, breed):
super().__init__(name)
self.breed = breed
def speak(self):
print(f"{self.name} barks!")
class Puppy(Dog):
def __init__(self, name, breed, age):
super().__init__(name, breed)
self.age = age
def speak(self):
print(f"{self.name} barks softly!")
puppy = Puppy("Charlie", "Beagle", 1)
puppy.speak() # Output: Charlie barks softly!
In this example:
Puppyinherits fromDog, which in turn inherits fromAnimal.- The
Puppyclass adds anageattribute and overrides thespeakmethod.
6. Multiple Inheritance
Python supports multiple inheritance, which means a child class can inherit from more than one parent class. However, this can create complexity, especially if multiple parent classes have methods with the same name. Python resolves these conflicts using the Method Resolution Order (MRO).
Example of Multiple Inheritance:
class Animal:
def speak(self):
print("Animal makes a sound")
class Dog:
def speak(self):
print("Dog barks")
class Hybrid(Animal, Dog):
def speak(self):
print("Hybrid speaks differently")
super().speak() # Calls the first parent class method in MRO
hybrid = Hybrid()
hybrid.speak() # Output: Hybrid speaks differently
# Animal makes a sound
In this example:
- The
Hybridclass inherits from bothAnimalandDog. - When
speak()is called on aHybridobject, Python uses the MRO to determine which parent class’s method to invoke.
7. The Method Resolution Order (MRO)
In the case of multiple inheritance, Python follows a specific order to search for a method in the class hierarchy. This order is defined by the C3 linearization algorithm, and can be checked using the mro() method.
Example of MRO:
class A:
def speak(self):
print("Class A speaks")
class B(A):
def speak(self):
print("Class B speaks")
class C(A):
def speak(self):
print("Class C speaks")
class D(B, C):
pass
# Check MRO for class D
print(D.mro())
Output:
[<class '__main__.D'>, <class '__main__.B'>, <class '__main__.C'>, <class '__main__.A'>, <class 'object'>]
In this example, the MRO for class D indicates the order in which Python will search for methods: D, B, C, A, and finally the base object class.
8. Private and Protected Members in Inheritance
- Protected members: Members that are intended to be protected (for internal use by subclasses) can be defined with a single underscore (
_), but this is a convention and doesn’t prevent access outside the class. - Private members: Members that should not be accessed outside the class are defined with double underscores (
__). Python performs name mangling to make these variables harder to access.
Example with Private and Protected Members:
class Parent:
def __init__(self):
self._protected = "This is protected"
self.__private = "This is private"
class Child(Parent):
def __init__(self):
super().__init__()
def show(self):
print(self._protected)
# print(self.__private) # This will cause an error
child = Child()
child.show()
In this example:
self._protectedcan be accessed by subclasses, butself.__privateis not directly accessible due to name mangling.
Summary of Inheritance Concepts:
- Inheritance: The mechanism of creating a new class from an existing class.
- Child Class: The class that inherits from a parent class.
- Parent Class: The class that is inherited from.
- Method Overriding: The child class can provide its own implementation of a method.
super(): Used to call methods from the parent class.- Multi-level Inheritance: Inheriting from a class that itself inherits from another class.
- Multiple Inheritance: A class can inherit from more than one parent class.
- Method Resolution Order (MRO): The order in which Python searches for methods in a class hierarchy.