Applying OOP in Real World Applications

Jaidev Singh Bhui
The Startup
Published in
8 min readAug 2, 2020
Source: https://francescolelli.info

As a programmer, or a computer science student, you might’ve heard or know something about the terms which are shown above. Actually you should have knowledge about these if you claim to be working in the software development or computer science field. Also, there is a chance that you might not have fully understood when and where all these features are applied in real life. This article focuses on the application of the most used programming paradigm — Object Oriented Programming, in real world problems.

So, Object Oriented Programming(OOP) is a programming paradigm(philosophy), which is based on the concept of “objects”, which can contain data, in the form of fields, and code, in the form of procedures.

There are four basic principles of OOPs: Encapsulation, Abstraction, Inheritance, Polymorphism, which will be discussed in the following sections.

I took part in Crio.do’s #iBelieveInDoing July challenge, in which we got to take part in some of their Micro-Experiences/Bytes focused on application of OOPs. I would recommend you all to go through that experience for some hands-on learning.

Here is a link to my previous article in the challenge on System Design: https://medium.com/@jaidev.bhui/a-high-level-view-of-cloud-computing-and-system-design-e56122326454

Let’s Get Started with OOP principles!

We’ll be taking the example of a chat app like Whatsapp.

Encapsulation

the action of enclosing something in or as if in a capsule.

Source: https://www.geeksforgeeks.org/

As the definition says, enclosing something in a capsule, the meaning of encapsulation in OOPs is quite intuitive, just like the other OOP principles.

Encapsulation is, containing all important information inside of an object, and only exposing selected information to the outside world. Attributes and behaviors are defined by code inside the class template. It helps in emulating real world objects/entities.

For Example, If we are writing code for a messaging app, we would have a message class, which would contain all the information about a particular message being sent, like — receiver, sender, message content, message id — and all it’s methods inside a single entity.

Encapsulation in Python

As we can see, all the attributes of the message are “encapsulated” together inside a bundle(class).

Encapsulation helps by:

  • Providing Security: to access any information about a message object we would have to go through the public getter and setter methods (setSender, setReceiver, getSender, getReceiver).
  • Protecting developers from common mistakes: Only public fields & methods accessible, so developers don’t accidentally change something dangerous.
  • Protects IP: code is hidden in a class, only public methods are accessible by the outside developers

What is the drawback if we don’t use encapsulation? — Duplication of code. Low maintainability. Inconsistent behavior. Difficult to test. Possible inappropriate access/modification from external methods.

Abstraction

the quality of dealing with ideas rather than events.

Going by the definition, this is exactly what a software or a product needs to have, for a better user experience, to be more user friendly.

What we mean by abstraction is, to hide all the complexities and implementations from the users, to make it easier for them to use it.

For example, if the user is driving a car, they don’t need to know how the clutch, brake or accelerator are working, but they are able to use them, to drive the car.

Photo by Christian Wiediger on Unsplash

Similarly in our chat app, the user doesn’t need to know how the message is being sent to the receiver, they just need to push the send button, and the work is done. Hence, this focuses on the “idea” of sending a message, and not on the “event” or “implementation” of sending it.

Another practical example of abstraction can be the Java Virtual Machine(JVM) — your code can use the exact same java methods irrespective of whether your code will run on Linux or Windows or any other OS. Underneath, a lot of things will change depending on the OS, which the user doesn’t need to know.

Why Abstraction is helpful:

  • Hide complex details from user
  • To the implementers(programmers) of the class, it is useful since it provides them with the flexibility to change things as long as the method signatures don’t change

What is the drawback if we don’t use abstraction? — Low maintainability because responsibilities are not clearly differentiated. Higher Complexity with larger code bases because many objects interact with others and it becomes difficult to add functionality without impacting others.

Inheritance

the action of inheriting(traits).

Source: https://codestall.wordpress.com/2017/09/20/inheritance-in-java/

Just like you inherit genes, features, traits from your ancestors, it is possible to inherit attributes, methods, data from one class to another.

Inheritance further strengthens the emulation of real world entities.

In our chat app, if we were to add some new features, like sending images or voice messages with the current code base, we would have to add new attributes particular to these new features, like image metadata, resolution, etc.

Not a good way to implement

Now, we could add those attributes as shown above, but this makes the code less maintainable, like if there was a need to add another feature we would have to add another attribute, which would be present with empty values in other message types, like there is no role of audio duration in text messages, so such information has no use for text messages, and similar case can be made for images.

Also, we would have to create many different getter and setter methods in the same class for different type of messages.

So, to make this code easier to understand, develop and maintain, we should use inheritance.

We will create a base class Message and then extend that to different message type classes:

Extending Base Message class

By extending the Message class, we can use all its fields in the child classes. This is helpful as all the message types have some common fields like sender and receiver.

Inheritance is useful:

  • It helps separate out common functionality and fields so that they can be reused across many other classes cleanly.
  • Avoids code redundancy.

Polymorphism

a feature of a programming language that allows routines to use variables of different types at different times.

Polymorphism means to have a function with same name performing a different task.

Source: https://prpckx.wordpress.com/

For example, in calculating area of a shape, for Circle it means pi*radius*radius, while for a rectangle it is length*breadth, similarly, in terms of speaking, for dogs it means to bark, while lions roar, cats meow, and so on.

Polymorphism is designing objects to share behaviors. Using inheritance, objects can override shared parent behaviors, with specific child behaviors. Polymorphism allows the same method to execute different behaviors in two ways: method overriding and method overloading.

Method Overriding/Runtime Polymorphism: child class provides its own implementation of the method defined in the parent class.

Method Overloading/Static Polymorphism: methods of same name, from the same class having difference in number and types of parameters.

Now in our app, let’s say, we don’t want to use the functionality provided by some of the methods in the base class, and want to implement our own functionality, by also not renaming the methods since that would mean changing all the client code that is presently invoking that method.

We would use Method Overriding, since we want our own implementation of the methods defined in the parent class.

In the base class, we are checking for validity of a message. Now, for Text Message it would be in terms of length, Image Message it would be in terms of its size. So, we should override this method to our needs in the child classes.

Method Overriding/ Runtime Polymorphism

In the case of our app, currently there are only default constructors(taking no arguments), but if the clients of this class want to set it to some default value of their choice, we would need to use Method Overloading:

Parameterized Constructor

Note: This form of method overloading is restrictive in Python since if you have two methods with the same name, only the second method definition holds good. The first one cannot be used.

So to give you a better idea, here is an example of Method overloading in Java:

Method Overloading in Java (Constructor Overload)

Now, when an Object of class Message is made, if we provide the parameters inside the constructor, the new constructor would run, and set the values given.

Why to use polymorphism:

  • Presents the ability to perform different actions using the same method signature.
  • Keeps code cleaner.

Conclusion

Object Oriented programming requires thinking about the structure of the program and planning at the beginning of coding. Looking at how to break up the requirements into simple, reusable classes that can be used to blueprint instances of objects. Overall, implementing OOP allows for better data structures and reusability, saving time in the long run.

Crio.Do

All of this was part of the various “Bytes” by Crio, in which I had to #learnbydoing.

I definitely learned a lot after completing this Micro Experience, and think that Crio is doing a great job in this period of stress and the situation created by the covid pandemic, by creating such an interactive online learning experience.

References

--

--

Jaidev Singh Bhui
The Startup

Professional Procrastinator and an aspiring Full Stack Web Developer.