Java Series #2b: Mastering the 4 Pillars of Object-Oriented Programming
A beginner-friendly breakdown of Encapsulation, Inheritance, Polymorphism, and Abstraction in Java.

I am a Full-stack dev turning ideas into sleek, functional experiences 🚀. I am passionate about AI, intuitive UI/UX, and crafting user-friendly platforms . I am always curious – from building websites to diving into machine learning and under the hood workings ✨. Next.js, Node.js, MongoDB, and Tailwind are my daily tools. I am here to share dev experiments, lessons learned, and the occasional late-night code breakthroughs. Always evolving, always building.
1. Encapsulation
Encapsulation = data hiding + controlled access.
What it solves
Without encapsulation, anyone can change your internal values → breaks logic, compromises security, causes unpredictable behavior.
How Java enforces it
Make variables private
Provide public getters/setters
Expose only what is necessary (API mindset)
Why it's important
Protects data from unintended modification
Helps maintainability
Allows validation before updating values
Quick Example
class BankAccount {
private double balance;
public double getBalance() {
return balance;
}
public void deposit(double amount) {
if (amount > 0) balance += amount;
}
}
Here, balance cannot be manipulated directly. Everything goes through controlled methods.
2. Inheritance
Inheritance = acquiring properties and behavior of another class.
Why it exists
To reuse code
To create a logical hierarchy
To enable polymorphism
Types
Single
Multilevel
Hierarchical
Hybrid
(Java does NOT support multiple class inheritance, only via interfaces.)
Real significance
The moment you do:
Parent p = new Child();
You enable late binding → runtime polymorphism.
super keyword
Access parent variable
Access parent method
Explicitly call parent constructor
Must be the first line in constructor
Example
class Animal {
void sound() { System.out.println("Animal sound"); }
}
class Dog extends Animal {
void sound() { System.out.println("Bark"); }
}
3. Polymorphism
Polymorphism = “many forms”.
Java supports two types:
3.1 Compile-time Polymorphism (Method Overloading)
Method name same, signature different.
Used for:
Convenience
Code readability
Handling multiple input types
Example:
void show(int a) {}
void show(String s) {}
3.2 Runtime Polymorphism (Method Overriding)
Actual method executed depends on the object, not the reference.
Enables:
Dynamic behavior
Flexibility
Plug-and-play object switching
Example:
Animal a = new Dog();
a.sound(); // Dog’s version runs
This is what “dynamic dispatch” means.
4. Abstraction
Abstraction = show essential stuff, hide unnecessary details.
Java gives two abstraction tools:
Abstract Classes
Interfaces
Why abstraction matters
Reduces complexity
Gives a clean API
Separates what to do from how to do
Abstract Class
Represents a partial blueprint.
Can contain:
Abstract methods
Concrete methods
Variables
Constructors
Can’t be instantiated.
Used when:
You want shared logic + some forceful implementation by child classes
You want to provide base functionality
Interface
Represents a full contract.
Before Java 8: only abstract methods
Now supports:
Default methods
Static methods
Private methods
Variables are always:public static final
Used when:
You want to achieve multiple inheritance
You want behavior but no implementation
You want to create standard APIs
| Feature | Abstract Class | Interface |
| Purpose | Partial blueprint (some implemented logic) | Full contract (no implementation originally; now possible via default methods) |
| Methods | Can have abstract + concrete | Abstract, default, static, private |
| Variables | Can have all types (instance, static, final) | Only public static final (constants) |
| Constructors | Allowed | Not allowed |
| Multiple Inheritance | Not supported | Supported (implements multiple interfaces) |
| Use Case | When subclasses share common logic or state | When classes should follow a common behavior |
| Access Modifiers | Methods can be public/protected | Methods are public by default (prior to overrides) |
| Speed | Slightly faster (no dynamic dispatch of default methods) | Slight overhead due to dynamic behavior |
| Real-World Analogy | A base template with partial implementation | A rulebook with must-follow behaviors |
Interview-Style Questions (with Clean Answers)
1. Difference between abstraction and encapsulation?
Answer:
Abstraction hides implementation details and shows only essential features (what to do).
Encapsulation hides data and restricts direct access to it (how data is protected).
Abstraction = Design Level
Encapsulation = Implementation Level
2. Can an abstract class have a constructor? Why?
Answer: Yes. To initialize common fields and to allow the derived class constructors to call the parent initialization logic.
3. Why doesn't Java allow multiple inheritance with classes?
Answer: To avoid ambiguity (Diamond Problem). Interfaces solve this by not storing state, so ambiguity doesn’t occur.
4. What is dynamic method dispatch?
Answer: Runtime mechanism in which the overridden method executed is based on the actual object, not the reference type.
Example:
Parent p = new Child();
p.show(); // Child’s show() runs
5. Can you override static methods in Java?
Answer: No. Static methods belong to the class, not the instance. You can "hide" them, but not override them.
6. Why do interfaces allow default methods?
Answer: To add new methods to interfaces without breaking existing implementations, supporting backward compatibility.
7. Why use interfaces when abstract classes exist?
Answer: Interfaces allow multiple inheritance and enforce a strict behavior contract across unrelated classes.
8. What is the difference between implements and extends?
Answer:
extends→ for inheriting class or abstract classimplements→ for adopting interface behavior
9. Can an interface extend another interface?
Answer: Yes, interfaces can extend multiple interfaces, enhancing capability composition.
10. Can a class implement multiple interfaces? Why allowed?
Answer: Yes, because interfaces don’t carry state → no ambiguity or DIAMOND PROBLEM.
Read intro to OOPs in → Understanding-oops-in-java




