Thread Safe Singleton pattern

Singleton Pattern : Define a class that has only one Instance.

Let’s try creating Thread Safe Singleton pattern.

public class Singleton {
private static Singleton instance;
private Singleton() {}

public static Singleton getInstance(){
if(instance == null)
{
instance = new Singleton();
}
return instance;
}
}

Sounds perfect right, We have made constructor as private , we have exposed static method getInstance(), if instance is null we create object of class Singleton assign it to instance and return the same.

This solution will work properly, when we have single core CPU and only 1 thread running.

What if there are 2 threads and both calls getInstance() method together, and context switching of thread occurs just after If statement but before creation of the Singleton object. We will end up creating 2 objects, Our class is no longer Singleton. 😟

public class Singleton {
private static final Singleton instance;

static {
instance = new Singleton();
}

private Singleton() {
}

public static Singleton getInstance() {

return instance;
}
}

Block of statement inside static block get executed when class is first loaded into JVM. A static block helps to initialize static data member.

No headache of creating object at runtime, sounds good right.

Cons

  • We are creating object and blocking space in memory even before its actually required.
  • There may be cases when you never used object created by Singleton and we unnecessary create object and block space in main memory.

So good idea to create object only when its required.

public class Singleton{
private static volatile Singletoninstance;
private Singleton() {}

public static synchronized Singleton getInstance(){
if(instance == null)
{
instance = new Singleton();
}
return instance;
}
}

In solution 1, root cause of issue was 2 threads were entering getInstance() at same time, How can we avoid this ?

Make method getInstance() synchronized, so that only one thread can enter at given time.

Is this solution Thread-Safe ?

YES

Is the solution Optimized ?

NO 😩

Let’s assume we have 4 threads, each of them calling getInstance() method. First thread will go inside getInstance() , As instance is null it will create the object[WRITE OPERATION]. Once first thread exits synchronizedblock, second thread will go and read instance [READ OPERATION]. Third thread needs to wait read instance[READ OPERATION] until second thread exits synchronizedblock.

Ideal solution should have WRITE OPERATIONS as sequential and READ OPERATION in parallel. In above solution as number of threads increases we are adding extra overhead even for simple READ OPERATION. If there are many call to getInstance it adds extra overhead.

public class Singleton{

private static volatile Singleton instance;
private Singleton() {}

private static Object key = new Object();

public static Singleton getInstance(){
if(instance != null)
{
return instance;
}

synchronized (key) {
if(instance == null)
{
instance = new Singleton();
}
}
return instance;
}

}

Perfect solution right, we enter into synchronized block only while creating instance. for reading instance, we don’t need to wait for any lock.

We need double check if instance is null or not inside the synchronized block because during the first check 2 threads can get instance as null as first check is not in synchronized block. If don’t do double checking we might end up creating multiple objects of Singleton instance.

NOTE : volatile is very important for java’s happens-before relationship, which is used when there are multiple threads executing simultaneously on multicore CPU for visibility.

Do check other implementation of thread safe singleton pattern,

  • Using Enum
  • Bill Pugh Singleton Implementation (Used static inner class). As inner class is lazily loaded when initialization of object occur