Why do we need to learn Object Oriented Programming?

Before learning the OOPS concepts, every developer should explore an answer to one critical question: Why OOPS is widely used in the software industry? Let's start with a good example to understand this. 

Suppose we're building a car rental system, where we have to manage different types of cars, customers, and rental transactions. Now the question is: How does object-oriented programming help in this scenario? There are several reasons:

  • OOPS helps us to break down the system into smaller, modular components. We can define classes for cars, customers, and rental transactions, each with its own data and behaviour. 
  • Using encapsulation, we can hide the internal workings of each class and protect the data from unauthorized access or modification.
  • By modularizing the system, we can reuse these classes across the system. It will save us time and make the development process easier.
  • By using the idea of inheritance, we can create specialized types of cars (Sedans, SUVs, etc.), derived from a base Car class. This will allow us to reuse common functionalities in the base class while adding specific features in the subclasses.
  • By using the idea of polymorphism, we can treat objects of different classes interchangeably. In our car rental system, this flexibility will let us write code that can handle renting different types of cars without worrying about their specific class.
  • Object-oriented programming will make code maintenance and extensibility easier. If we need to make changes to the system, we can modify or extend specific classes without affecting others. So it will reduce the chances of introducing bugs.

If you observe, object-oriented programming provides several benefits: enhanced code structure, code reusability, better security, better maintainability, flexibility and so on. Now let's understand this idea in detail from another perspective!

Algorithms + Data Structures = Programs

Mohan had thoroughly read a book by Niklaus Wirth, which covered fundamental concepts of programming. He boasted: "I know everything about how to write a program. Why do I need to learn OOPS?"

A wise developer replied: "Because what Niklaus said is one part of the story - A program is a combination of two things: Information (data) and a set of instructions for manipulating that information (algorithms). But it turns out that we are not just writing programs, we are writing software."

Mohan asked: "Well, what is the difference?"

The wise developer explained: "We write a program to perform a specific task like sorting a linked list, finding the shortest path in a graph, or displaying a 'hello world' message on the console. Software, on the other hand, is a collection of programs that work together to perform several tasks."

Now Mohan asked: "What is OOPS and how can it help me?"

The wise developer replied: " Modern software is often extremely complex, consisting of millions of lines of code and operating on terabytes of data. It is usually too complex for a single person to understand. So, we need a way to organize these instructions in a way that makes our code: Easier to understand, explain, reuse, extend and maintain. Object oriented programming has been a popular paradigm for achieving these goals."

Building System: The OOP Way

Before discussing object-oriented programming, it is important to understand what an object is. An object is a logical construct that consists of user-defined data and a set of operations for manipulating that data. It can be thought of as a combination of data and behaviour (Data + Operations = Object). So, OOP is a way of organizing and structuring a program around objects.

Thinking in an object-oriented way can help us understand the software problem we are trying to solve. It helps us to break a problem into smaller, more manageable pieces and think about each piece individually, rather than trying to understand the entire problem at once.

For example, let's consider the task of building an inventory management system for a bookstore. The requirements of this system might include:

  • Storing metadata for each book: name, author, and price.
  • Allowing books to be added to or removed from the inventory.
  • Providing the ability to search for books by metadata.

OOPS example to build an inventory management system for a bookstore

To build your system using an object-oriented approach, you will need to:

  • Identify objects in your system.
  • Identify relationships and responsibilities of these objects.
  • Identify attributes (data) and operations (methods) for each object.

To further refine your design using an object-oriented approach, write down your analysis and go through the steps again. Ask questions like:

  • Does the author need to be a class or a string?
  • How should I store books so that they can be searched easily?
  • Does the order of search results matter? What if the user wants to sort books by price?

Asking these types of questions can also help you:

  • How to understand which objects are necessary and which ones are not?
  • How to avoid bugs in your system?
  • How to deliver software that meets the needs of the user?

Here is a simple example of how your classes might look like:

class Book {
    private String name;
    private String authorName;
    private float price;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getAuthorName() {
        return authorName;
    }

    public void setAuthorName(String authorName) {
        this.authorName = authorName;
    }

    public float getPrice() {
        return price;
    }

    public void setPrice(float price) {
        this.price = price;
    }
}

class Inventory {
    private Book[] bookList;

    public Book[] searchItem(String name) {
        // Implementation for searching an item
    }

    public void addItem(Book book) {
        // Implementation for adding an item
    }

    public Book removeItem(Book book) {
        // Implementation for removing an item
    }
}

As another example, let's consider the task of building a chess game. To get started, think about the physical objects you need in order to play a game of chess in real life. These might include:

  • A board with 8x8 squares, where the game is played.
  • Chess pieces of different types like pawns, bishops, knights, kings, queens, and rooks, for each player.
  • Two players to play the game.

From the requirements above, we can identify the following objects: player, board, square, pawn, bishop, knight, king, queen, rook, game, etc. These objects can be used to structure the chess game.

Wait!

It is common when designing a real-world system to model objects according to physical objects that we can see in the real world. In the case of a chess game, we could create a separate class for each noun identified in the requirements. But a wise programmer always thinks twice before writing any code!

As Robert C. Martin wrote in Book Clean Code: "The ratio of time spent reading versus writing is well over 10 to 1." This means that we spend a lot of time reading code, so it is important to make it easy to read in order to make it easier to write.

When designing your system, consider whether each piece requires a separate class, or if they are instances of the same class with different types. For example, do you need a separate player class, or can players be considered external initiators interacting with the system? Remember, there is no single correct answer, but a simple design with fewer entities is often a good starting point.

One such answer could be:

enum Color {BLACK, WHITE}

class ChessPiece {
    enum Type {PAWN, BISHOP, KNIGHT, KING, QUEEN, ROOK}
    Type type;
    Color color;
    Square currentPos;
    // Moves the piece to the target square.
    void move(Square targetSquare) {
        // Implementation for moving the chess piece
    }
}

class Square {
    Color color;
    ChessPiece piece;
    String position;
}

class Board {
    Square[][] squares = new Square[8][8];
    // Initialize game board and setup pieces
    Board() {
        // Implementation for initializing the game board and setting up pieces
    }
}

class Game {
    ChessPiece[] activePieces;
    ChessPiece[] capturedPieces;

    void startGame() {
        // Implementation for starting the game
    }

    void stopGame() {
        // Implementation for stopping the game
    }

    void pauseGame() {
        // Implementation for pausing the game
    }
}

Mohan said: "So, just like in the world of algorithms, where we try to divide a problem into smaller parts in order to find an optimal solution using the computer, we are dividing our program into smaller parts in order to find an optimal code for developers."

The wise developer replied: "Yes, that's correct. There are many other programming paradigms that were created with this goal in mind. But that's a topic for another time. For now, you should focus on improving your object-oriented programming skills."

Conclusion

Objects are an integral part of every software system that you interact with in your daily life. Deciding which objects you need and which you don't require careful analysis of your requirements. Remember that object-oriented programming provides a mental model for how to structure your software. Once you understand this concept, you can use it in any programming language.

Enjoy learning, enjoy OOP!

Share Your Insights

☆ 16-week live DSA course
☆ 16-week live ML course
☆ 10-week live DSA course

More from EnjoyAlgorithms

Self-paced Courses and Blogs

Coding Interview

Machine Learning

System Design

Our Newsletter

Subscribe to get well designed content on data structure and algorithms, machine learning, system design, object orientd programming and math.