Composition in Java | Example Program

Composition in Java is one of the core concepts of object-oriented programming. It is different from inheritance.

Inheritance is defined as Is-A relationship whereas, composition is defined as Has-A relationship. Both composition and inheritance are design techniques and can be used for the purpose of code reusability.

Composition is a more specialized form of aggregation. In other words, it is a more restrictive and strong form of aggregation.

Java composition differs from aggregation is that aggregation represents a Has-A relationship between two objects having their own lifetime, but composition represents a Has-A relationship that contains an object that cannot exist on its own.

In other words, child object does not have its own lifetime. If the parent object is destroyed, the child object will also be destroyed. The child object cannot exist without the existence of its parent object.

In simple words, a composition can be defined as if a parent object contains a child object and the child object cannot exist on its own without having the existence of parent object, it is called composition in java.

It can be achieved by using an instance variable that refers to another object. Let’s understand the basic meaning of composition with help of realtime examples.

Realtime Example of Composition in Java


1. We live in a house. House can have many rooms. But there is no independent life of room and it cannot also associate to two different houses.

If we destroy the house, the room will be automatically destroyed. So, we can say that a room is PART-OF the house.

2. Another real-time example of composition in Java is “Car and Engine”. A car has an engine. In other words, an engine is a PART-OF car. Here, a car is a whole, and engine is a part of that car.

If the car is destroyed then its engine will be destroyed as well. So, without the existence of car, there is no life of an engine. The life of an engine is totally dependent on the life cycle of car.


Let’s understand it programmatically with the help of an example program. Look at the following program code to understand better.

Example 1:

public class Engine 
{  
   private String type;
   private int horsePower;
 
   Engine(String type, int horsePower) {
      this.type = type;
      this.horsePower = horsePower;
   }
   public String getType() {
      return type;	
   }  
   public int getHorsePower() {
      return horsePower;	
   }
   public void setType(String type){
      this.type = type;	
   }
   public void setHorsePower(int horsePower){
      this.horsePower = horsePower;	
   }
}
public class Car 
{
   private final String name;
   private final Engine engine; // Composition.
 
   public Car(String name, Engine engine) {
      this.name = name;	
      this.engine = engine;
   }
   public String getName() {
      return name;	
   }
   public Engine getEngine() {
      return engine;	
   }
}
public class Test {
public static void main(String[] args) 
{
// Creating an object of Engine class.
   Engine engn = new Engine("Petrol", 300);
  
// Creating an object of Car class.
   Car car = new Car("Alto", engn);
   System.out.println("Name of car: " +car.getName()+ "\n" +"Type of engine: " +engn.getType()+ "\n" + "Horse power of Engine: " +engn.getHorsePower());
 }
}
Output:
      Name of car: Alto
      Type of engine: Petrol
      Horse power of Engine: 300

In this example, we have created a class Engine that contains two private attributes: type (string) and horsePower (integer). It has a constructor that takes two parameters, type and horsePower, and initializes the attributes with these values. In addition to it, there are getter and setter methods for both attributes to retrieve and update their values.

Then, we have created a class Car containing two private attributes: name (string) and engine (of class type Engine). The class has a constructor that takes a name and an engine object as parameters.

The name attribute is assigned the provided name, and the engine attribute is assigned the provided engine object. The class contains getter methods for both attributes to retrieve their values.

We have defined a class Test that contains the main method, which serves as the entry point for the program. Inside the main method, we have created an instance of the Engine class by passing the values “Petrol” and 300 to its constructor.

Then, we have created an instance of the Car class by passing the values “Alto” and the previously created Engine instance to its constructor. This shows the concept of composition, where the Car class contains an instance of the Engine class as one of its attributes.

At last, the program code prints out the name of the car, type of engine, and horse power of the engine using the getter methods of the Car and Engine classes.

Features of Composition in Java


There are several important features about composition that are as follows:

1. Composition represents a has-a relationship in Java. In other words, it represents PART-OF relationship.

2. It is a more restrictive form of aggregation.

3. In composition, both the entities are associated with each other.

4. A composition between two entities happens when an object (in other words, parent object) contains a composed object ( in other words, child object), and the composed object cannot exist without the existence of that object.

For example, a library contains a number of books on the same or different subjects. If the library gets destroyed for any reason, all books placed within that library will be destroyed automatically. That is, books cannot exist without a library of school or college.

5. It can be achieved by using an instance variable that refers to other objects.

Advantages of using Composition over Inheritance


There are several benefits of using composition in Java over inheritance. They are as follows:

1. Composition is better than inheritance because it allows to reuse of code and provides visibility control on objects.

2. Java doesn’t allow multiple inheritance but by using composition we can achieve it easily.

3. Composition grants better test-ability of a class.

4. By using composition, we can easily replace the implementation of a composed class with a better and improved version.

5. Composition allows the changing of member objects at runtime so that we can dynamically change the behavior of our program.

⇐ Prev Next ⇒

Please share your love