Abstraction in Java is the process of hiding internal implementation details and showing only essential functionality to the user. It focuses on what an object does rather than how it does it.
Key features of abstraction
- Abstraction hides the complex details and shows only essential features.
- Abstract classes may have methods without implementation and must be implemented by subclasses.
- By abstracting functionality, changes in the implementation do not affect the code that depends on the abstraction.
How to Achieve Abstraction in Java?
Java provides two ways to implement abstraction, which are listed below:
- Abstract Classes (Partial Abstraction)
- Interface (100% Abstraction)
Real-Life Example of Abstraction
The television remote control is the best example of abstraction. It simplifies the interaction with a TV by hiding all the complex technology. We don't need to understand how the tv internally works, we just need to press the button to change the channel or adjust the volume.
AbstractionExample:
Java
// Working of Abstraction in Java
abstract class Geeks {
abstract void turnOn();
abstract void turnOff();
}
// Concrete class implementing the abstract methods
class TVRemote extends Geeks {
@Override
void turnOn() {
System.out.println("TV is turned ON.");
}
@Override
void turnOff() {
System.out.println("TV is turned OFF.");
}
}
// Main class to demonstrate abstraction
public class Main {
public static void main(String[] args) {
Geeks remote = new TVRemote();
remote.turnOn();
remote.turnOff();
}
}
OutputTV is turned ON.
TV is turned OFF.
Explanation:
- Geeks is abstract class defining turnOn() and turnOff() methods.
- TVRemote class implements the abstract methods with specific logic.
- Main class uses Geeks remote = new TVRemote(); to interact without knowing the internal implementation.
Abstract class
An abstract class is a way to achieve abstraction in Java. It is declared using the abstract keyword and can contain both abstract methods non abstract methods. Abstract classes cannot be instantiated directly and are meant to be extended by subclasses. Besides abstraction, abstract classes also allow code reusability through shared behavior and state.
Consider a classic “shape” example, perhaps used in a computer-aided design system or game simulation. The base type is “shape” and each shape has a color, size, and so on. From this, specific types of shapes are derived(inherited)-circle, square, triangle, and so on — each of which may have additional characteristics and behaviors. For example, certain shapes can be flipped. Some behaviors may be different, such as when you want to calculate the area of a shape. The shape hierarchy shows both the similarities that all shapes share and the differences that makes each one unique.
Abstract Classes and methodsExample:
This program defines an abstract class Shape with an abstract method area() and a concrete method getColor(), demonstrating partial abstraction. It shows how an abstract class can have constructors and both implemented and unimplemented methods.
Java
abstract class Shape {
String color;
// these are abstract methods
abstract double area();
public abstract String toString();
// abstract class can have the constructor
public Shape(String color)
{
System.out.println("Shape constructor called");
this.color = color;
}
// this is a concrete method
public String getColor() { return color; }
}
class Circle extends Shape {
double radius;
public Circle(String color, double radius)
{
// calling Shape constructor
super(color);
System.out.println("Circle constructor called");
this.radius = radius;
}
@Override double area()
{
return Math.PI * Math.pow(radius, 2);
}
@Override public String toString()
{
return "Circle color is " + super.getColor()
+ "and area is : " + area();
}
}
class Rectangle extends Shape {
double length;
double width;
public Rectangle(String color, double length,
double width)
{
// calling Shape constructor
super(color);
System.out.println("Rectangle constructor called");
this.length = length;
this.width = width;
}
@Override double area() { return length * width; }
@Override public String toString()
{
return "Rectangle color is " + super.getColor()
+ "and area is : " + area();
}
}
public class Test {
public static void main(String[] args)
{
Shape s1 = new Circle("Red", 2.2);
Shape s2 = new Rectangle("Yellow", 2, 4);
System.out.println(s1.toString());
System.out.println(s2.toString());
}
}
Example:
This program demonstrates abstraction using an abstract class Animal with an abstract method makeSound(). Subclasses Dog and Cat provide specific implementations, and objects are accessed via the abstract reference type.
Java
// Abstract Class declared
abstract class Animal {
private String name;
public Animal(String name) {
this.name = name;
}
public abstract void makeSound();
public String getName() {
return name;
}
}
// Abstracted class
class Dog extends Animal {
public Dog(String name) {
super(name);
}
public void makeSound()
{
System.out.println(getName() + " barks");
}
}
// Abstracted class
class Cat extends Animal {
public Cat(String name) {
super(name);
}
public void makeSound()
{
System.out.println(getName() + " meows");
}
}
// Driver Class
public class Geeks {
// Main Function
public static void main(String[] args)
{
Animal myDog = new Dog("ABC");
Animal myCat = new Cat("XYZ");
myDog.makeSound();
myCat.makeSound();
}
}
OutputABC barks
XYZ meows
Interface
Interfaces is a blueprint of a class used to achieve 100% abstraction in Java. It can contain abstract methods and constants but no method bodies (except default and static methods from Java 8 onward).
Implementation: To implement an interface we use the keyword “implements” with class.
Example: Below is the Implementation of Abstraction using Interface.
Java
// Define an interface named Shape
interface Shape {
double calculateArea(); // Abstract method for
// calculating the area
}
// Implement the interface
// in a class named Circle
class Circle implements Shape {
private double r; // radius
// Constructor for Circle
public Circle(double r) {
this.r = r;
}
// Implementing the abstract method
// from the Shape interface
public double calculateArea()
{
return Math.PI * r * r;
}
}
// Implement the interface in a
// class named Rectangle
class Rectangle implements Shape {
private double length;
private double width;
// Constructor for Rectangle
public Rectangle(double length, double width)
{
this.length = length;
this.width = width;
}
// Implementing the abstract
// method from the Shape interface
public double calculateArea() {
return length * width;
}
}
// Main class to test the program
public class Main {
public static void main(String[] args)
{
// Creating instances of Circle and Rectangle
Circle c = new Circle(5.0);
Rectangle rect = new Rectangle(4.0, 6.0);
System.out.println("Area of Circle: "
+ c.calculateArea());
System.out.println("Area of Rectangle: "
+ rect.calculateArea());
}
}
OutputArea of Circle: 78.53981633974483
Area of Rectangle: 24.0
Advantages of Abstraction
- Abstraction makes complex systems easier to understand by hiding the implementation details.
- Abstraction keeps different part of the system separated.
- Abstraction maintains code more efficiently.
- Abstraction increases the security by only showing the necessary details to the user.
Disadvantages of Abstraction
- It can add unnecessary complexity if overused.
- May reduce flexibility in implementation.
- Makes debugging and understanding the system harder for unfamiliar users.
- Overhead from abstraction layers can affect performance.
Abstract Classes and Abstract Methods
Abstract Classes | Abstract Methods |
---|
An abstract class is a class that is declared with an abstract keyword. | An abstract method is a method that is declared without implementation. |
---|
An abstract class may have both abstract methods (methods without implementation) and concrete methods (methods with implementation) | An abstract method must always be redefined in the subclass, thus making overriding compulsory or making the subclass itself abstract. |
---|
Any class that contains one or more abstract methods must also be declared with an abstract keyword. | An abstract method is a method that is declared without an implementation (i.e., without a body) and is meant to be overridden in a subclass. |
---|
Common Mistakes to Avoid
The common mistakes that can occur and we should avoid when working with Abstraction in Java are listed below:
- Not Implementing Abstract Methods: Always make sure that the abstract methods are implemented in the concrete subclass.
- Overusing Abstraction: Avoid making everything abstract when it’s not required. Use abstraction only when it enhances the design.
- Inconsistent Method Signatures in Subclasses: When you override abstract methods, please make sure the method signature matches exactly, any mistake can cause errors.