How to create Immutable class in Java

In Java, an immutable class means that we can't change the content of an object once it's been created. All wrapper classes (such as Integer, Boolean, Byte, Short) and the String class are immutable in Java. We can even make our immutable class. Before proceeding, review the immutability features to ensure that you have a thorough knowledge of the concept.

 

The following are the prerequisites:

  • To prevent the creation of child classes, the class must be designated as final.
  • Direct access to data members in the class must be prohibited by declaring them private.
  • Data members in the class must be specified as final so that the value cannot be changed after the object has been created.
  • A parameterized function Object() { [native code] } should make a deep copy to initialize all fields, preventing data members from being updated using an object reference.
  • Deep copying of objects should be done in getter methods to return a copy instead of the original object reference)


Example:


// Java Program to Create An Immutable Class


// Importing required classes

import java.util.HashMap;

import java.util.Map;


// Class 1

// An immutable class

final class Student {


// Member attributes of final class

private final String name;

private final int regNo;

private final Map<String, String> metadata;


// Constructor of immutable class

// Parameterized constructor

public Student(String name, int regNo,

Map<String, String> metadata)

{


// This keyword refers to current instance itself

this.name = name;

this.regNo = regNo;


// Creating Map object with reference to HashMap

// Declaring object of string type

Map<String, String> tempMap = new HashMap<>();


// Iterating using for-each loop

for (Map.Entry<String, String> entry :

metadata.entrySet()) {

tempMap.put(entry.getKey(), entry.getValue());

}


this.metadata = tempMap;

}


// Method 1

public String getName() { return name; }


// Method 2

public int getRegNo() { return regNo; }


// Note that there should not be any setters


// Method 3

// User -defined type

// To get meta data

public Map<String, String> getMetadata()

{


// Creating Map with HashMap reference

Map<String, String> tempMap = new HashMap<>();


for (Map.Entry<String, String> entry :

this.metadata.entrySet()) {

tempMap.put(entry.getKey(), entry.getValue());

}

return tempMap;

}

}


// Class 2

// Main class

class TestImmutableClass{


// Main driver method

public static void main(String[] args)

{


// Creating Map object with reference to HashMap

Map<String, String> map = new HashMap<>();


// Adding elements to Map object

// using put() method

map.put("1", "first");

map.put("2", "second");


Student s = new Student("ABC", 101, map);


// Calling the above methods 1,2,3 of class1

// inside main() method in class2 and

// executing the print statement over them

System.out.println(s.getName());

System.out.println(s.getRegNo());

System.out.println(s.getMetadata());


// Uncommenting below line causes error

// s.regNo = 102;


map.put("3", "third");

// Remains unchanged due to deep copy in constructor

System.out.println(s.getMetadata());

s.getMetadata().put("4", "fourth");

// Remains unchanged due to deep copy in getter

System.out.println(s.getMetadata());

}

}



Post a Comment

0 Comments