Wednesday, May 20, 2009

Ways to implement singleton pattern in Java

There are many, time tested ways to implement Singleton pattern in Java all having its own advantage and drawbacks.

A simple and less confusing way to implement this is

public class
{
public final static Bar bar = new Bar();
private Bar()
{
// This prevents class instantiation from outside
}
public static Bar getBar()
{
return bar;
}
}

This is cleaner and readable code, but it does not give us an option of lazy initialization.
When you have a very large object or heavy construction code AND also have other accessible static methods or fields that might be used before an instance is needed, then and we need the lazy initialization option.

public class Bar
{
public final static Bar bar ;
private Bar()
{
// This prevents class instantiation from outside
}
public static Bar getBar()
{
synchronized(Bar.class)
{
if(bar == null)
{
bar = new Bar();
}
return bar;
}
}
}

The synchronized block helps to keep this instance creation thread safe.

If we are using Java 5 or above, we can use the additional feature provided by it for Double Checked locking. Without this, other threads are not guaranteed by the JMM ( Java Memory Model) to see the changes to its value.

You can refer this classic article on this subject:

http://www.cs.umd.edu/~pugh/java/memoryModel/DoubleCheckedLocking.html

public class Bar
{
public static volatile Bar bar ;

private Bar()
{
// This prevents class instantiation from outside
}

public static Bar getBar()
{
synchronized(Bar.class)
{
if(bar == null)
{
bar = new Bar();
}
return bar;
}
}
}


Note the volatile keyword which does the trick.

Adding
protected Object clone()
{
throw new CloneNotSupportedException();
}

Would make Singletons better !!.

we have to choose the design based on requirement and make use of Singletons very carefully in our applications.

Cheers
Vinay