Interview Questions, Answers and Tutorials

Choosing between composition and inheritance

Choosing between composition and inheritance

Hey there! Today we will learn about two important ways to build things in programming: composition and inheritance. Imagine you’re building with Lego bricks—sometimes you want to stick bricks together in different ways (composition), and sometimes you want to start with a big piece and add smaller pieces on top (inheritance). Let’s see how this works in Python!

Inheritance

Inheritance is like saying “is-a.” If a new thing is just a special kind of another thing, we use inheritance.

Example:

Imagine we have a basic class called Animal. Then we make a new class called Dog that inherits from Animal because a dog is an animal.

class Animal:
    def __init__(self, name):
        self.name = name

    def make_sound(self):
        return "Some generic sound"

class Dog(Animal):
    def make_sound(self):
        return "Bark"

my_dog = Dog("Fido")
print(my_dog.name)        # Output: Fido
print(my_dog.make_sound())  # Output: Bark




Here, Dog inherits from Animal, so Dog can do everything Animal can, but it also has its own special make_sound method.

Composition

Composition is like saying “has-a.” If a new thing is made up of other things, we use composition.

Example:

Imagine we have a class called Engine and a class called Car that has an engine.

class Engine:
    def __init__(self, horsepower):
        self.horsepower = horsepower

class Car:
    def __init__(self, model, engine):
        self.model = model
        self.engine = engine

my_engine = Engine(200)
my_car = Car("Toyota", my_engine)
print(my_car.model)           # Output: Toyota
print(my_car.engine.horsepower)  # Output: 200




Here, Car has an Engine. The car is made up of an engine, among other things.

When to Use Inheritance vs. Composition

  1. Use Inheritance when:
    • The new class is a specialized version of the existing class (is-a relationship).
    • You want to reuse code from the parent class.
  2. Use Composition when:
    • The new class is made up of other classes (has-a relationship).
    • You want to combine different pieces together to create complex behavior.

Practice Questions

Question 1:

Create a base class called Bird with a method fly. Then create a subclass Penguin that inherits from Bird but overrides the fly method to print “Penguins can’t fly”.

Solution:

class Bird:
    def fly(self):
        return "Flies in the sky"

class Penguin(Bird):
    def fly(self):
        return "Penguins can't fly"

penguin = Penguin()
print(penguin.fly())  # Output: Penguins can't fly

Question 2:

Create a class called Battery with an attribute capacity. Then create a class Phone that has a Battery object.

Solution:

class Battery:
    def __init__(self, capacity):
        self.capacity = capacity

class Phone:
    def __init__(self, brand, battery):
        self.brand = brand
        self.battery = battery

battery = Battery(4000)
phone = Phone("Samsung", battery)
print(phone.brand)         # Output: Samsung
print(phone.battery.capacity)  # Output: 4000

  • Inheritance is for “is-a” relationships. Use it when one thing is a specialized version of another.
  • Composition is for “has-a” relationships. Use it when one thing is made up of other things.

Remember, both inheritance and composition are tools to help you build better programs. Use them wisely, and you’ll be able to create amazing things with your code!