We all learn about Object-Oriented Programming (OOP), classes, objects, and those four famous pillars: encapsulation, inheritance, polymorphism, and abstraction. Honestly, I never understood why we even learn this, but it turns out it does have some real-world use cases, and that’s exactly what we’re going to explore.
In this blog, we’re going to build one of the most popular applications, a To-Do app, using OOP concepts in Python.
![](https://prod-files-secure.s3.us-west-2.amazonaws.com/4ce5980e-ec00-425c-9a63-cd0a031307fa/099f0e11-be27-42f6-8fe4-e0f488fce19b/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB4666TQSNQG2%2F20260902%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20260902T171539Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjEP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEaCXVzLXdlc3QtMiJHMEUCIQCAd%2FHUgklkNcJfsx88fWEZqJkvn5ttGPH2GTgtJ1cAtwIgCuWD5PNLcnuBiaDeXsowOiZZI2ub8dr4n5npde1asw0qiAQIyP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FARAAGgw2Mzc0MjMxODM4MDUiDBcGVwbximLHC%2F9apyrcA5K%2FgjV7onPKu3A5F05IP%2BzB5f79JJWoFdiM%2BKSY6eYV5WawVePkJ5pJExNbvph2lFHYFQ10mCP829QypUHC1zlE6NX40P%2F4hsjh7rlJaO7JhLoMwCkF%2BL3CNIYLN%2B5fU5cF%2BJAvPt8XzGsbdK%2FLO4ikPRItgLQIUiE9Ac1T5GAi8guG44VGHOXTv1hWfGZAfUFR%2BCyJyeU%2FGycSabFiJJmXR1dsrHyTT5qr1TKsVxwYU2QY69Xx8Q%2B9vTExd%2BZMD5Hmldr4VbeVBeYkWaM4L%2BX60aWBimIGcHOts0hkwuNWglHoLQTEUZamTwcRv0xpgjD7zKG7zxY%2BcTWLvdpVqUkYtPmZBfxl7v0sEbpQAGqjMg2p8bMvrQTCfp1wRPzKMYn0oUjIwJ%2FG2tGjXlYI7gJxVIw2ie1ZuowJoJqbKZ54AW%2FNJKufNpkeOGK0eDYljSyVDEy65oKzZIfND4fFrUR97sJb9PfI2DZ%2B3QxhxGtHM%2FlxPjrXui3sNnB7T6Zsg3ZNu7mYsdV2Opb%2BNZ0V%2FOoZ8llyFm0dIPI8oDTZnLNi69gUsot1j47WNWKHVrIvUN9jW1SDZdFNlSODzyzvaZXb2Ib763VPK3UHEBVZJco932rNDod6Nfqghj92MNf24NQGOqUBFluY6%2BVA4l5sKyJkNrfx7LXy%2Bvm80KQXqWFE%2B1GhKQuXf09WmXi9UimlsppALmep%2BKl9I9SqNWtE61V%2BlWDff7dcoWE%2B5QZYlSChYFDcuneTsVCnNFltwQxbTVDT75A38BdnApx1l0EFSQknX5FHAs%2FKH%2FZMi2amFmTqLa5y%2B1E1LtgDwInpKXpPbPQnSJQ%2BH9vwxPf9dRkFpf3j3EIk6ZK1tlBI&X-Amz-Signature=73a2339df94aaf8bb4eb06f1ef0c5f8d87159f5919f455609411c9bab3c65a1a&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject)
# Basics “jargon”
Before we dive in, there are a few jargons you should be familiar with:
1. **Class** – Think of it as a blueprint that defines what an object should look like and what it can do.
2. **Object** – A real-world instance created from a class; it’s the actual thing you work with.
3. **Attributes** – These are the variables inside a class that hold data about the object.
4. **Methods** – These are functions inside a class that define the object’s behavior or actions.
<empty-block/>
## What Are These "Four Pillars" Everyone Talks About?
Almost every interviewer or viva examiner loves this question: *“Explain the four pillars of OOP.”*
They are **encapsulation**, **inheritance**, **polymorphism**, and **abstraction**.
But what exactly do these fancy terms mean in simple language? 
![](https://prod-files-secure.s3.us-west-2.amazonaws.com/4ce5980e-ec00-425c-9a63-cd0a031307fa/91e1efc0-5bd7-4788-8476-630e8dddf256/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB4666TQSNQG2%2F20260902%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20260902T171539Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjEP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEaCXVzLXdlc3QtMiJHMEUCIQCAd%2FHUgklkNcJfsx88fWEZqJkvn5ttGPH2GTgtJ1cAtwIgCuWD5PNLcnuBiaDeXsowOiZZI2ub8dr4n5npde1asw0qiAQIyP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FARAAGgw2Mzc0MjMxODM4MDUiDBcGVwbximLHC%2F9apyrcA5K%2FgjV7onPKu3A5F05IP%2BzB5f79JJWoFdiM%2BKSY6eYV5WawVePkJ5pJExNbvph2lFHYFQ10mCP829QypUHC1zlE6NX40P%2F4hsjh7rlJaO7JhLoMwCkF%2BL3CNIYLN%2B5fU5cF%2BJAvPt8XzGsbdK%2FLO4ikPRItgLQIUiE9Ac1T5GAi8guG44VGHOXTv1hWfGZAfUFR%2BCyJyeU%2FGycSabFiJJmXR1dsrHyTT5qr1TKsVxwYU2QY69Xx8Q%2B9vTExd%2BZMD5Hmldr4VbeVBeYkWaM4L%2BX60aWBimIGcHOts0hkwuNWglHoLQTEUZamTwcRv0xpgjD7zKG7zxY%2BcTWLvdpVqUkYtPmZBfxl7v0sEbpQAGqjMg2p8bMvrQTCfp1wRPzKMYn0oUjIwJ%2FG2tGjXlYI7gJxVIw2ie1ZuowJoJqbKZ54AW%2FNJKufNpkeOGK0eDYljSyVDEy65oKzZIfND4fFrUR97sJb9PfI2DZ%2B3QxhxGtHM%2FlxPjrXui3sNnB7T6Zsg3ZNu7mYsdV2Opb%2BNZ0V%2FOoZ8llyFm0dIPI8oDTZnLNi69gUsot1j47WNWKHVrIvUN9jW1SDZdFNlSODzyzvaZXb2Ib763VPK3UHEBVZJco932rNDod6Nfqghj92MNf24NQGOqUBFluY6%2BVA4l5sKyJkNrfx7LXy%2Bvm80KQXqWFE%2B1GhKQuXf09WmXi9UimlsppALmep%2BKl9I9SqNWtE61V%2BlWDff7dcoWE%2B5QZYlSChYFDcuneTsVCnNFltwQxbTVDT75A38BdnApx1l0EFSQknX5FHAs%2FKH%2FZMi2amFmTqLa5y%2B1E1LtgDwInpKXpPbPQnSJQ%2BH9vwxPf9dRkFpf3j3EIk6ZK1tlBI&X-Amz-Signature=a065dbf43a5481322e4e4bd69b004ae33bb2d911307302995f19b35986191113&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject)
## Encapsulation: Keeping Things Tidy
Think of **encapsulation** as good housekeeping for your code. In our To-Do app, we’ll create classes that keep related data and methods bundled together while hiding the messy details from the outside world.
For example, our `TodoItem` class takes care of everything related to a single task:
```python
class TodoItem:
    def __init__(self, title):
        self.__title = title
        self.__completed = False

    def mark_complete(self):
        self.__completed = True

    def get_status(self):
        return "Completed" if self.__completed else "Pending"
```
The beauty here? Other parts of the app don’t need to know *how* the task status is stored or changed.
They just call `mark_complete()` and get the job done.
The internal logic stays hidden and protected inside the class.
***Note:*** `__init__` is called automatically every time you create a new object from a class.
It’s known as the **constructor**, the method that initializes the object with its starting values.
---
## Inheritance: Don’t Repeat Yourself
Tasks in our To-Do app can come in different types – work tasks, personal tasks, or recurring ones.
Rather than rewriting the same logic for each, we can create a base class and let others build on it.
![](https://prod-files-secure.s3.us-west-2.amazonaws.com/4ce5980e-ec00-425c-9a63-cd0a031307fa/fde22252-2638-40b7-898b-5743783952f9/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB4666TQSNQG2%2F20260902%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20260902T171539Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjEP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEaCXVzLXdlc3QtMiJHMEUCIQCAd%2FHUgklkNcJfsx88fWEZqJkvn5ttGPH2GTgtJ1cAtwIgCuWD5PNLcnuBiaDeXsowOiZZI2ub8dr4n5npde1asw0qiAQIyP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FARAAGgw2Mzc0MjMxODM4MDUiDBcGVwbximLHC%2F9apyrcA5K%2FgjV7onPKu3A5F05IP%2BzB5f79JJWoFdiM%2BKSY6eYV5WawVePkJ5pJExNbvph2lFHYFQ10mCP829QypUHC1zlE6NX40P%2F4hsjh7rlJaO7JhLoMwCkF%2BL3CNIYLN%2B5fU5cF%2BJAvPt8XzGsbdK%2FLO4ikPRItgLQIUiE9Ac1T5GAi8guG44VGHOXTv1hWfGZAfUFR%2BCyJyeU%2FGycSabFiJJmXR1dsrHyTT5qr1TKsVxwYU2QY69Xx8Q%2B9vTExd%2BZMD5Hmldr4VbeVBeYkWaM4L%2BX60aWBimIGcHOts0hkwuNWglHoLQTEUZamTwcRv0xpgjD7zKG7zxY%2BcTWLvdpVqUkYtPmZBfxl7v0sEbpQAGqjMg2p8bMvrQTCfp1wRPzKMYn0oUjIwJ%2FG2tGjXlYI7gJxVIw2ie1ZuowJoJqbKZ54AW%2FNJKufNpkeOGK0eDYljSyVDEy65oKzZIfND4fFrUR97sJb9PfI2DZ%2B3QxhxGtHM%2FlxPjrXui3sNnB7T6Zsg3ZNu7mYsdV2Opb%2BNZ0V%2FOoZ8llyFm0dIPI8oDTZnLNi69gUsot1j47WNWKHVrIvUN9jW1SDZdFNlSODzyzvaZXb2Ib763VPK3UHEBVZJco932rNDod6Nfqghj92MNf24NQGOqUBFluY6%2BVA4l5sKyJkNrfx7LXy%2Bvm80KQXqWFE%2B1GhKQuXf09WmXi9UimlsppALmep%2BKl9I9SqNWtE61V%2BlWDff7dcoWE%2B5QZYlSChYFDcuneTsVCnNFltwQxbTVDT75A38BdnApx1l0EFSQknX5FHAs%2FKH%2FZMi2amFmTqLa5y%2B1E1LtgDwInpKXpPbPQnSJQ%2BH9vwxPf9dRkFpf3j3EIk6ZK1tlBI&X-Amz-Signature=f52594cae2f1706158fd44edc1d94101231d0036abde61181e82a4847ecc70af&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject)
```python
class Task:
    def __init__(self, title):
        self.title = title
        self.completed = False

    def mark_complete(self):
        self.completed = True

class WorkTask(Task):
    def __init__(self, title, deadline):
        super().__init__(title)
        self.deadline = deadline

```
Here, `WorkTask` inherits all the features of `Task` and adds a `deadline` of its own.
If we ever want to add a new common method (like saving to a file), we can do it once in the parent class, and all child classes will get it automatically.
***Note: ***`self` simply refers to the **current object** — the specific instance of the class that’s being worked on
![](https://prod-files-secure.s3.us-west-2.amazonaws.com/4ce5980e-ec00-425c-9a63-cd0a031307fa/d872710a-4011-4eff-abe3-ce4c418f9615/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB4666TQSNQG2%2F20260902%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20260902T171539Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjEP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEaCXVzLXdlc3QtMiJHMEUCIQCAd%2FHUgklkNcJfsx88fWEZqJkvn5ttGPH2GTgtJ1cAtwIgCuWD5PNLcnuBiaDeXsowOiZZI2ub8dr4n5npde1asw0qiAQIyP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FARAAGgw2Mzc0MjMxODM4MDUiDBcGVwbximLHC%2F9apyrcA5K%2FgjV7onPKu3A5F05IP%2BzB5f79JJWoFdiM%2BKSY6eYV5WawVePkJ5pJExNbvph2lFHYFQ10mCP829QypUHC1zlE6NX40P%2F4hsjh7rlJaO7JhLoMwCkF%2BL3CNIYLN%2B5fU5cF%2BJAvPt8XzGsbdK%2FLO4ikPRItgLQIUiE9Ac1T5GAi8guG44VGHOXTv1hWfGZAfUFR%2BCyJyeU%2FGycSabFiJJmXR1dsrHyTT5qr1TKsVxwYU2QY69Xx8Q%2B9vTExd%2BZMD5Hmldr4VbeVBeYkWaM4L%2BX60aWBimIGcHOts0hkwuNWglHoLQTEUZamTwcRv0xpgjD7zKG7zxY%2BcTWLvdpVqUkYtPmZBfxl7v0sEbpQAGqjMg2p8bMvrQTCfp1wRPzKMYn0oUjIwJ%2FG2tGjXlYI7gJxVIw2ie1ZuowJoJqbKZ54AW%2FNJKufNpkeOGK0eDYljSyVDEy65oKzZIfND4fFrUR97sJb9PfI2DZ%2B3QxhxGtHM%2FlxPjrXui3sNnB7T6Zsg3ZNu7mYsdV2Opb%2BNZ0V%2FOoZ8llyFm0dIPI8oDTZnLNi69gUsot1j47WNWKHVrIvUN9jW1SDZdFNlSODzyzvaZXb2Ib763VPK3UHEBVZJco932rNDod6Nfqghj92MNf24NQGOqUBFluY6%2BVA4l5sKyJkNrfx7LXy%2Bvm80KQXqWFE%2B1GhKQuXf09WmXi9UimlsppALmep%2BKl9I9SqNWtE61V%2BlWDff7dcoWE%2B5QZYlSChYFDcuneTsVCnNFltwQxbTVDT75A38BdnApx1l0EFSQknX5FHAs%2FKH%2FZMi2amFmTqLa5y%2B1E1LtgDwInpKXpPbPQnSJQ%2BH9vwxPf9dRkFpf3j3EIk6ZK1tlBI&X-Amz-Signature=65d70caac8c50b0b5c5b3fb51095102c2aa6a6770d0bddf35047767bfc7f4ef0&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject)
---
## Polymorphism: Same Action, Different Behavior
Polymorphism sounds fancy, but it’s simple: the same function name can have different behaviors depending on the object using it.
In our To-Do app, different types of tasks might have different ways of showing details.
```python
class Task:
    def show(self):
        print(f"Task: {self.title}")

class WorkTask(Task):
    def show(self):
        print(f"Work Task: {self.title} (Deadline: {self.deadline})")

class PersonalTask(Task):
    def show(self):
        print(f"Personal Task: {self.title}")

```
Now, when we call `show()` on a list of mixed tasks, each one behaves appropriately without us writing multiple function names:
```python
tasks = [WorkTask("Finish report", "2025-11-10"), PersonalTask("Buy groceries")]

for t in tasks:
    t.show()

```
---
## Abstraction: Simplifying the Complex
Users don’t need to know how the entire task system works — they just want to add, complete, or view tasks.
Abstraction helps us hide the complexity behind simple, clean interfaces.
```python
from abc import ABC, abstractmethod

class TaskManager(ABC):
    @abstractmethod
    def add_task(self, title):
        pass

    @abstractmethod
    def complete_task(self, title):
        pass


class SimpleTaskManager(TaskManager):
    def __init__(self):
        self.tasks = []

    def add_task(self, title):
        self.tasks.append(Task(title))

    def complete_task(self, title):
        for t in self.tasks:
            if t.title == title:
                t.mark_complete()
```
Here, `TaskManager` defines *what* actions a manager should support,
and `SimpleTaskManager` decides *how* those actions actually work internally.
The outside world just calls `add_task()` or `complete_task()` without caring about the internal logic.
---
## Putting It All Together
Here’s what makes OOP so powerful, these four pillars work together to keep your project clean and scalable:
- Each task encapsulates its own data and logic
- Common functionality is inherited across different types of tasks
- Actions like `show()` work polymorphically for all task types
- Complex details are abstracted behind simple, clean interfaces
That’s how OOP turns a simple To-Do app into a maintainable, organized system you can easily expand over time.
![](https://prod-files-secure.s3.us-west-2.amazonaws.com/4ce5980e-ec00-425c-9a63-cd0a031307fa/d092bb7d-e24b-4f59-8ae6-862055ab0d41/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB4666TQSNQG2%2F20260902%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20260902T171539Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjEP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEaCXVzLXdlc3QtMiJHMEUCIQCAd%2FHUgklkNcJfsx88fWEZqJkvn5ttGPH2GTgtJ1cAtwIgCuWD5PNLcnuBiaDeXsowOiZZI2ub8dr4n5npde1asw0qiAQIyP%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FARAAGgw2Mzc0MjMxODM4MDUiDBcGVwbximLHC%2F9apyrcA5K%2FgjV7onPKu3A5F05IP%2BzB5f79JJWoFdiM%2BKSY6eYV5WawVePkJ5pJExNbvph2lFHYFQ10mCP829QypUHC1zlE6NX40P%2F4hsjh7rlJaO7JhLoMwCkF%2BL3CNIYLN%2B5fU5cF%2BJAvPt8XzGsbdK%2FLO4ikPRItgLQIUiE9Ac1T5GAi8guG44VGHOXTv1hWfGZAfUFR%2BCyJyeU%2FGycSabFiJJmXR1dsrHyTT5qr1TKsVxwYU2QY69Xx8Q%2B9vTExd%2BZMD5Hmldr4VbeVBeYkWaM4L%2BX60aWBimIGcHOts0hkwuNWglHoLQTEUZamTwcRv0xpgjD7zKG7zxY%2BcTWLvdpVqUkYtPmZBfxl7v0sEbpQAGqjMg2p8bMvrQTCfp1wRPzKMYn0oUjIwJ%2FG2tGjXlYI7gJxVIw2ie1ZuowJoJqbKZ54AW%2FNJKufNpkeOGK0eDYljSyVDEy65oKzZIfND4fFrUR97sJb9PfI2DZ%2B3QxhxGtHM%2FlxPjrXui3sNnB7T6Zsg3ZNu7mYsdV2Opb%2BNZ0V%2FOoZ8llyFm0dIPI8oDTZnLNi69gUsot1j47WNWKHVrIvUN9jW1SDZdFNlSODzyzvaZXb2Ib763VPK3UHEBVZJco932rNDod6Nfqghj92MNf24NQGOqUBFluY6%2BVA4l5sKyJkNrfx7LXy%2Bvm80KQXqWFE%2B1GhKQuXf09WmXi9UimlsppALmep%2BKl9I9SqNWtE61V%2BlWDff7dcoWE%2B5QZYlSChYFDcuneTsVCnNFltwQxbTVDT75A38BdnApx1l0EFSQknX5FHAs%2FKH%2FZMi2amFmTqLa5y%2B1E1LtgDwInpKXpPbPQnSJQ%2BH9vwxPf9dRkFpf3j3EIk6ZK1tlBI&X-Amz-Signature=ccf041fc7db0c80fc553915b76698ffd9b14b631dcc0d82202edb301d088bd5f&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject)
<empty-block/>