Give an example of a program that shows modular design.

1 answer

Certainly! A common example of a program that exhibits modular design is a simple task management application. This application is divided into various modules that handle different aspects of the functionality, making it easier to maintain and extend. Below is a simplified version of such a program in Python:

Example: Task Management Application

Project Structure

task_manager/
│
├── task.py          # Module for task-related operations
├── user.py          # Module for user-related operations
├── database.py      # Module for database operations
└── main.py          # Entry point of the application

Module: task.py

This module handles tasks and their related operations.

# task.py

class Task:
    def __init__(self, title, completed=False):
        self.title = title
        self.completed = completed

    def complete(self):
        self.completed = True

    def __str__(self):
        return f"{self.title} [{'✓' if self.completed else '✗'}]"

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

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

    def complete_task(self, index):
        if 0 <= index < len(self.tasks):
            self.tasks[index].complete()

    def list_tasks(self):
        return [str(task) for task in self.tasks]

Module: user.py

This module deals with user-related tasks.

# user.py

class User:
    def __init__(self, username):
        self.username = username
        self.tasks = []

    def add_task(self, task):
        self.tasks.append(task)

    def get_tasks(self):
        return self.tasks

Module: database.py

This module simulates database operations (could be expanded to use an actual database).

# database.py

class Database:
    def __init__(self):
        self.data = []

    def save(self, record):
        self.data.append(record)

    def fetch_all(self):
        return self.data

Entry Point: main.py

This is the entry point for the application that ties everything together.

# main.py

from task import TaskManager
from user import User
from database import Database

def main():
    db = Database()
    user = User("Alice")
    task_manager = TaskManager()
    
    while True:
        action = input("Choose an action: add, complete, list, or exit: ")
        if action == 'add':
            title = input("Enter task title: ")
            task_manager.add_task(title)
            user.add_task(title)
            db.save(title)
        elif action == 'complete':
            index = int(input("Enter task index to complete: "))
            task_manager.complete_task(index)
        elif action == 'list':
            tasks = task_manager.list_tasks()
            print("\n".join(tasks))
        elif action == 'exit':
            break
        else:
            print("Invalid action!")

if __name__ == "__main__":
    main()

Explanation

  1. Modularity: Each module (task.py, user.py, database.py) encapsulates related functionalities and can be independently developed and tested.
  2. Maintainability: If you need to add a feature (like saving tasks to a file instead of using a database), you can do so by just modifying or adding functionality in the database.py module without affecting other parts of the application.
  3. Reusability: Functions within each module can be reused in different parts of the application or even in other applications.

This structure of using modules is crucial in software design as it promotes better organization, separation of concerns, and ultimately a more maintainable codebase.