Object-Oriented Programming in Python

Introduction

OOP is a programming paradigm that helps you structure your code in a more organized and efficient way by using objects and classes. In this article, we’ll explain the basics of OOP and illustrate how it can be applied in the automotive industry with simple examples but you can apply in any other scenarios.

What is Object-Oriented Programming?

Object-Oriented Programming (OOP) is a way to organize your code around objects, which can represent real-world entities. Each object is an instance of a class, and a class defines the blueprint for objects.

Key Concepts of OOP:
  1. Class: A blueprint for creating objects. It defines attributes and methods that the objects will have.
  2. Object: An instance of a class. It can have unique values for its attributes.
  3. Attributes: Variables that hold data specific to the object.
  4. Methods: Functions defined inside a class that describe the behaviors of the objects.

Example in Automotive Industry: A Car Management System

Let’s consider a simple example of a car management system where we have different types of cars with specific attributes and methods. We’ll define a class Car that can be used to create different car objects.

Step 1: Define a Class

First, we’ll define a class Car with attributes like make, model, year, and status, and methods to start and stop the car.

class Car:
def __init__(self, make, model, year):
self.make = make
self.model = model
self.year = year
self.status = "stopped"

def start(self):
self.status = "running"
print(f"{self.make} {self.model} has started.")

def stop(self):
self.status = "stopped"
print(f"{self.make} {self.model} has stopped.")

# Creating an object (instance) of the class Car
car1 = Car("Tata", "Harrier", 2020)
Step 2: Use the Object

Now, we’ll use the object car1 to start and stop the car.

# Starting the car
car1.start() # Output: Tata Harrier has started.

# Checking the status of the car
print(car1.status) # Output: running

# Stopping the car
car1.stop() # Output: Tata Harrier has stopped.

# Checking the status of the car again
print(car1.status) # Output: stopped
Step 3: Creating Multiple Objects

We can create multiple car objects from the Car class to represent different cars in our system.

car2 = Car("Honda", "Civic", 2018)
car3 = Car("Ford", "Mustang", 2021)

car2.start() # Output: Honda Civic has started.
car3.start() # Output: Ford Mustang has started.

print(car2.status) # Output: running
print(car3.status) # Output: running

car2.stop() # Output: Honda Civic has stopped.
car3.stop() # Output: Ford Mustang has stopped.

Benefits of Using OOP in the Automotive Industry

  1. Modularity: Each car can be represented as an object, making the code easier to manage and understand.
  2. Reusability: The Car class can be used to create any number of car objects, reducing code duplication.
  3. Scalability: New features and functionalities can be added to the class without affecting existing code.
  4. Maintainability: Changes to the class definition automatically apply to all instances, making maintenance simpler.

Real-Time Business Scenarios

Example 1: Managing a Fleet of Vehicles

In a car rental company, you need to manage a fleet of vehicles. You can create a Car class to keep track of each vehicle’s status.

class Car:
def __init__(self, make, model, year, car_id):
self.make = make
self.model = model
self.year = year
self.car_id = car_id
self.status = "available"

def rent(self):
self.status = "rented"
print(f"{self.make} {self.model} (ID: {self.car_id}) has been rented.")

def return_car(self):
self.status = "available"
print(f"{self.make} {self.model} (ID: {self.car_id}) has been returned.")

# Creating car objects
car1 = Car("Toyota", "Camry", 2020, "CAR001")
car2 = Car("Honda", "Civic", 2018, "CAR002")

# Renting and returning cars
car1.rent() # Output: Toyota Camry (ID: CAR001) has been rented.
car2.rent() # Output: Honda Civic (ID: CAR002) has been rented.

print(car1.status) # Output: rented
print(car2.status) # Output: rented

car1.return_car() # Output: Toyota Camry (ID: CAR001) has been returned.
car2.return_car() # Output: Honda Civic (ID: CAR002) has been returned.
Example 2: Tracking Maintenance Records

A service center needs to keep track of maintenance records for each car.

class Car:
def __init__(self, make, model, year, car_id):
self.make = make
self.model = model
self.year = year
self.car_id = car_id
self.maintenance_records = []

def add_maintenance(self, date, description):
record = {"date": date, "description": description}
self.maintenance_records.append(record)
print(f"Added maintenance record to {self.make} {self.model} (ID: {self.car_id}).")

def show_maintenance(self):
print(f"Maintenance records for {self.make} {self.model} (ID: {self.car_id}):")
for record in self.maintenance_records:
print(f"Date: {record['date']}, Description: {record['description']}")

# Creating car objects
car1 = Car("Toyota", "Camry", 2020, "CAR001")
car2 = Car("Honda", "Civic", 2018, "CAR002")

# Adding maintenance records
car1.add_maintenance("2023-05-01", "Oil change")
car2.add_maintenance("2023-06-15", "Brake inspection")

# Showing maintenance records
car1.show_maintenance()
# Output:
# Maintenance records for Toyota Camry (ID: CAR001):
# Date: 2023-05-01, Description: Oil change

car2.show_maintenance()
# Output:
# Maintenance records for Honda Civic (ID: CAR002):
# Date: 2023-06-15, Description: Brake inspection

Minor Project: Flight Management System

Scenario

Let’s create a simple flight management system where we can manage flights and passengers. We will first develop this system without using OOP, and then we will refactor it using OOP to demonstrate the benefits of the OOP approach.

Part 1: Without Using OOP

1. Define Data Structures

We’ll use dictionaries and lists to store information about flights and passengers.

# Flights data
flights = [
{"flight_number": "AI101", "destination": "New York", "capacity": 200, "booked_seats": 0},
{"flight_number": "BA202", "destination": "London", "capacity": 150, "booked_seats": 0}
]

# Passengers data
passengers = []
2. Functions to Manage Flights and Passengers
# Function to add a new flight
def add_flight(flight_number, destination, capacity):
flight = {"flight_number": flight_number, "destination": destination, "capacity": capacity, "booked_seats": 0}
flights.append(flight)

# Function to book a flight
def book_flight(flight_number, passenger_name):
for flight in flights:
if flight["flight_number"] == flight_number:
if flight["booked_seats"] < flight["capacity"]:
flight["booked_seats"] += 1
passengers.append({"name": passenger_name, "flight_number": flight_number})
print(f"Passenger {passenger_name} booked on flight {flight_number}.")
else:
print(f"Sorry, flight {flight_number} is fully booked.")
return
print(f"Flight {flight_number} not found.")

# Function to display all flights
def display_flights():
for flight in flights:
print(f"Flight {flight['flight_number']} to {flight['destination']} - {flight['booked_seats']}/{flight['capacity']} booked.")

# Function to display passengers on a flight
def display_passengers(flight_number):
print(f"Passengers on flight {flight_number}:")
for passenger in passengers:
if passenger["flight_number"] == flight_number:
print(passenger["name"])

# Example usage
add_flight("DL303", "Paris", 180)
book_flight("AI101", "John Doe")
book_flight("BA202", "Jane Smith")
display_flights()
display_passengers("AI101")

Part 2: Using OOP

1. Define Classes

We’ll create classes to represent flights and passengers, encapsulating related data and behaviors.

class Flight:
def __init__(self, flight_number, destination, capacity):
self.flight_number = flight_number
self.destination = destination
self.capacity = capacity
self.booked_seats = 0
self.passengers = []

def book_seat(self, passenger):
if self.booked_seats < self.capacity:
self.booked_seats += 1
self.passengers.append(passenger)
print(f"Passenger {passenger.name} booked on flight {self.flight_number}.")
else:
print(f"Sorry, flight {self.flight_number} is fully booked.")

def display_passengers(self):
print(f"Passengers on flight {self.flight_number}:")
for passenger in self.passengers:
print(passenger.name)

class Passenger:
def __init__(self, name):
self.name = name
2. Functions to Manage Flights and Passengers
class FlightManagementSystem:
def __init__(self):
self.flights = []

def add_flight(self, flight_number, destination, capacity):
flight = Flight(flight_number, destination, capacity)
self.flights.append(flight)
print(f"Flight {flight_number} to {destination} added with capacity {capacity}.")

def book_flight(self, flight_number, passenger_name):
passenger = Passenger(passenger_name)
for flight in self.flights:
if flight.flight_number == flight_number:
flight.book_seat(passenger)
return
print(f"Flight {flight_number} not found.")

def display_flights(self):
for flight in self.flights:
print(f"Flight {flight.flight_number} to {flight.destination} - {flight.booked_seats}/{flight.capacity} booked.")

def display_passengers(self, flight_number):
for flight in self.flights:
if flight.flight_number == flight_number:
flight.display_passengers()
return
print(f"Flight {flight_number} not found.")

# Example usage
system = FlightManagementSystem()
system.add_flight("AI101", "New York", 200)
system.add_flight("BA202", "London", 150)
system.book_flight("AI101", "John Doe")
system.book_flight("BA202", "Jane Smith")
system.display_flights()
system.display_passengers("AI101")

Benefits of OOP

  1. Modularity: Code is organized into classes, making it easier to manage and understand.
  2. Reusability: Classes and methods can be reused across different parts of the program without duplication.
  3. Encapsulation: Data and methods are bundled together, keeping them hidden from the outside and reducing complexity.
  4. Maintainability: Changes can be made to individual classes without affecting the entire system, making the code easier to maintain and extend.
  5. Inheritance: New classes can be created based on existing classes, promoting code reuse and reducing redundancy.

Conclusion

In this article, we introduced the basics of Object-Oriented Programming (OOP) in Python using examples from the automotive industry. We covered key concepts such as classes, objects, attributes, and methods, and demonstrated how they can be used to create and manage car objects in a car management system. Understanding OOP will help you write more organized, reusable, and maintainable code.

Practice Exercise

  1. Define a Truck class with attributes like make, model, year, and load_capacity.
  2. Create methods to load_cargo and unload_cargo.
  3. Create objects for different trucks and use the methods to manage cargo operations.

Happy coding!

Leave a Reply