Creating Immutable class in java


What is Immutable class?
Any change made to object of immutable class produces new object.
Example- String is Immutable class in java, any changes made to Sting object produces new String object.

Creating Immutable class >
    
1) Final class - Make class final so that it cannot be inherited

2) private member variable -> Making member variables private ensures that fields cannot be accessed outside class.


3) final member variable -> Make member variables final so that they can be assigned only once.

4) Constructor -> Initialize all fields in constructor.
     assign all mutable member variable using new keyword.

5) Don't provide setter methods in class/ provide only getter methods.

6) object of immutable class - Any change made to object of immutable class produces new object.
  object of mutable class -  Any change made to object of mutable class doesn't produces new object.
   - Integer, String are immutable class,
         any changes made to object of these classes produces new object.
       so return reference variable of Integer.
   - HashMap is mutable class,
         any changes made to HashMap object won't produce new HashMap object.
         so return copy/clone of object, not reference variable of HashMap.*/



Program to create Immutable class>
import java.util.HashMap;
/** ImmutableClass
* 1) Final class - Make class final so that it cannot be inherited
*/
final class ImmutableClass{
  
  /**
  * 2) private member variable -> Making fields private ensures that fields
                                  cannot be accessed outside class.
  * 3) final member variable -> Make field final
                                  so that they can be assigned only once.
  */
   private final Integer id; //Immutable member variable
   private final String name; //Immutable member variable
   private final HashMap<Integer,String> map; //mutable member variable
   /** 4) Constructor -> Initialize all fields in constructor.
    *            assign all mutable member variable using new keyword.
    */
   public ImmutableClass(Integer id, String name, HashMap<Integer,String> map){
       this.id=id;
       this.name=name;
      
       //assign all mutable member variable using new keyword.
       this.map=new HashMap<Integer, String>(map);
   }
            
   /* getter method for id.*/
   public Integer getId() {
      /** 5a) Integer is immutable class,
       *     any changes made to Integer object produces new Integer object.
       *     so return reference variable of Integer.
       */
       return id;
   }
   /* getter method for name.*/
   public String getName() {
      /** 5b) String is immutable class,
       *     any changes made to Sting object produces new String object.
       *     so return reference variable of String.
       */
       return name;
   }
   /* Method returns clone of HashMap. */
   public HashMap<Integer, String> getMap() {
      /** 5c) HashMap is mutable class,
       *     any changes made to HashMap object won't produce new HashMap object.
       *     so return copy/clone of object, not reference variable of HashMap.*/
       return (HashMap<Integer, String>) map.clone();
   }
  
   /** 6) Don't provide setter methods in class */
}
/*
* Copyright (c), AnkitMittal JavaMadeSoEasy.com
* Main class for testing ImmutableClass
*/
public class ImmutableClassTest{
   public static void main(String[] args) {
     
      Integer localId=new Integer(1); //local
     
      String localName=new String("ankit"); //local
     
       HashMap<Integer, String> localMap = new HashMap<Integer,String>(); //local
       localMap.put(11, "audi");
    
       ImmutableClass immutableClass = new ImmutableClass(localId, localName, localMap);
      
       System.out.println("----Display ImmutableClass members before changing----");
       System.out.println(immutableClass.getName());  // "ankit"
       System.out.println(immutableClass.getId());        // 1
       System.out.println(immutableClass.getMap());   //{11=audi}
       //Comparing ImmutableClass members with local before changing
       System.out.println(localName==immutableClass.getName()); //true
       System.out.println(localId==immutableClass.getId());      //true
       System.out.println(localMap == immutableClass.getMap()); //false
      
       //change local
       localId = new Integer(2);
       localName = new String("mittal");
       localMap.put(12, "ferarri");
      
       System.out.println("\n----Display ImmutableClass members after changing----");
       System.out.println(immutableClass.getName());  // "ankit"
       System.out.println(immutableClass.getId());        // 1
       System.out.println(immutableClass.getMap());   //{11=audi}
       //Comparing ImmutableClass members with local after changing
       System.out.println(localName==immutableClass.getName()); //false
       System.out.println(localId==immutableClass.getId());      //false
       System.out.println(localMap == immutableClass.getMap()); //false
   }
}
/*OUTPUT
----Display ImmutableClass members before changing----
ankit
1
{11=audi}
true
true
false
----Display ImmutableClass members after changing----
ankit
1
{11=audi}
false
false
false
*/


Interview question>
Should we make the class and methods both final?
No, If we have made class final than there is no need to make methods final, because final class cannot be extended and hence methods cannot be overridden.

Example of immutable classes in java>
  • Integer (Wrapper class)
  • Double (Wrapper class)
  • Long (Wrapper class)
  • Short (Wrapper class)
  • Byte (Wrapper class)
  • And all other Wrapper classes.


Advantages of using Immutable  class >

  • Key in HashMap - Immutable classes are can be used as key in Map (HashMap etc.)

  • HashCode is cached - JVM caches the HashCode of Immutable classes used in application. JVM need not to calculate hashcode again. Hence, performance of application is improved significantly.

  • If Immutable class throws Exception - If Immutable class throws Exception, they are never left in undesirable state.




RELATED LINKS>

String pool/ String literal pool/ String constant pool in java

Creating Immutable class in java



Labels: Core Java
eEdit
Must read for you :