- Some ways to create Singleton class in Java
- Table of contents
- Eager Initialization Singleton class
- Lazy Initialization Singleton class
- Thread-safe Singleton class
- Double-checking Singleton class
- Bill Pugh Singleton class
- Enum Singleton class
- How to create singleton java
- Learn Latest Tutorials
- Preparation
- Trending Technologies
- B.Tech / MCA
- Javatpoint Services
- Training For College Campus
Some ways to create Singleton class in Java
In this article, we will find something out about ways to create Singleton class in Java. Before understanding it, we should read up on this Singleton class.
Table of contents
Eager Initialization Singleton class
public class Singleton public static Singleton instance = new Singleton(); private Singleton() <> // do other things // . >
public class Singleton private static Singleton instance = new Singleton(); private Singleton() <> public static Singleton getInstance() return instance; > // do other things // . >
These versions have the same performance because modern JVM implementations are almost certain to inline the call to the static factory method and the public final field.
- Benefits
- With public final field
- The declarations make it clear that the class is a singleton: the public static field is final, so it will always contains the same object reference.
- The public final field version is simpler than the static factory version.
- It gives us the flexibility to change the our mind about whether the class should be a singleton without changing its API.
- Applying with generic types.
Constructor[] constructors = Singleton.class.getDeclaredConstructors(); Constructor constructor = constructors[0]; constructor.setAccessible(true); Singleton tmpSingleton = (Singleton) constructor.newInstance(new Object[0]);
To solve this problem, we need to modify the constructor of Singleton with public final field ’s version or the static method — getInstance() of Singleton with static factory ’s version to make it throw an exception if it’s asked to create a second instance.
public class Singleton private static boolean isCreatedInstance = false; private static final Singleton instance = new Singleton(); private Singleton() if (isCreatedInstance) throw new IllegalStateException(); > else isCreatedInstance = true; > > public static Singleton getInstance() return instance; > // do other things // . >
Lazy Initialization Singleton class
public class Singleton private static final Singleton instance = null; private Singleton() <> public static Singleton getInstance() if (Objects.isNull(instance)) // Use Objects with Java 7 or later version singleton = new Singleton(); > return singleton; > >
- Benefits
- This way prevents the problem about using singleton with static final field when we do not want to create singleton class’s instance at class loading time.
- Exception handling will be used in the method.
- Only use in single-threaded environment.
- Reflection attacks.
Thread-safe Singleton class
public class Singleton private static final Singleton instance = null; private Singleton() <> public static synchronized Singleton getInstance() if (Objects.isNull(instance)) // Use Objects with Java 7 or later version singleton = new Singleton(); > return singleton; > >
This way will improve the Lazy Initialization Singleton class ’s version when it can use in multi-threaded environment. Let’s have a closer look at Singleton pattern on single core and two cores CPU.
- Singleton on a Single core CPU
- Singleton on a two cores CPU
- Singleton on a multiple cores CPU Let’s suppose we have four cores.
T1 thread is running first, then T2 needs to wait for T1 to leave the synchronized method to be able to read instance. And if on our two other cores, we have two other threads, T3 and T4, who also want to read our instance variable, well those threads will have to wait for T2 to leave the getInstance() method.
At this point, instance has been created, so all the reads could happen at the same time, but since our getInstance() method is synchronized, no more than one thread can enter it at a given time. So no more than one thread can read instance at the same time, and this is really a performance hit because the more cores we have, the more time we’re going to lose since the reads cannot be made in parallel. Of course, all the reads could be made in parallel in a correct way, but the synchronization of the method does not allow that.
- Benefits and Drawbacks
- Benefits
- Use in multithread environment.
- It still has the benefits of Lazy Initialization Singleton class ’s version.
- Drawbacks
- getInstance() method is synchronized so it causes slow performance as multiple threads can’t access it simultaneously.
- Benefits
Double-checking Singleton class
public class Singleton private volatile static final Singleton instance; private Singleton() <> public static Singleton getInstance() if (Objects.isNull(instance)) // Use Objects with Java 7 or later version synchronized (Singleton.class) if (Objects.isNull(instance)) instance = new Singleton(); > > > return instance; > >
When we see about this code, we can find that we still have encountered the performance overhead at the first time, only one thread will be entered into the synchronized block of static class, the remained threads will be waited for some times. After the first moment, the performance for using Singleton class do not affected by the first null checked condition. Note that using volatile keyword for instance variable, it will tell the compiler that always to read / write from the main memory, not use CPU cache or local thread stack.
- Some possible issues with Double-Checking Singleton
- Singleton on a Multiple Cores CPU In our Singleton class, we have a private static field called instance of type Singleton. It is just a pointer that will point to our only instance of the Singleton class. But the creation of this object is, in fact, a two step process.
- Memory Allocation (a)
- The copy of the pointer that points to the newly allocated memory into the Singleton field, which is called instance. (b)
- The construction process of the Singleton object. This allocated memory belongs to the Singleton class, it has a certain number of fields, certain number of methods, … (c)
Between the b step and the c step, we do not know which one is going to be executed first. If the construction process is executed first, then the copy of the pointer, everything will be fine because we cannot observe a non null instance pointer that points to a non fully built piece of memory.
But if the copy of the pointer occurs first, and that we read this instance field in another thread, then we will have visibility on a portion of memory that has been allocated but is not fully initialized yet, and this weird case could happen in the double-check locking. We do not have the guarantee that this second case will not happen, and if it does then very bad things can happen to our applications because basically what we can do is call methods on an object that is not fully built, that is completely corrupted at this step.
- Benefits
- Performance overhead gets reduced, so it can be use in high performance multithread environment.
- Having benefits of Thread-safe Singleton class ’s version.
private static final Singleton instance; public static Singleton getInstance() if (Objects.isNull(instance)) // Use Objects with Java 7 or later version synchronized (Singleton.class) if (Objects.isNull(instance)) instance = new Singleton(); > > > return instance; >
- If instance is not null, we read it and return it. Here we have the read operation on the instance field of the Singleton class. Is it a synchronized or volatile read? It is no, because instance is not a volatile variable, and this test is not a synchronized block. We have written it outside of the synchronized block on purpose, so it is not inside this synchronized block, then it is not a synchronized read neither.
- If instance is null, we create it and return it. Obviously there is a write operation. Is it a synchronized or volatile write? It is not a volatile write because instance is not a volatile variable, but it takes place in a synchronized block, so it is a synchronized write.
So we have a non synchronized read that is supposed to return the value set by a synchronized write. Do we have the guarantee that the read will get the value set by the write? For that we need a happens-before link.
For that to have this guarantee, we have a happens-before link between read and write operation. The read operation is outside of the synchronized block, and the fact is we do not have this happens-before link because happens-before link are created between synchronized or volatile writes and synchronized or volatile reads.
So this code is buggy because there is no happens-before link between the read returning the value and the write that sets it.
This is very subtle bug indeed, it is not very obvious to see this bug.
Bill Pugh Singleton class
public class Singleton private Singleton() <> public static Singleton getInstance() return BillPughSingleton.instance; > private static class BillPughSingleton private static final Singleton instance = new Singleton(); > >
- Benefits
- Thread safe but does not using synchronized keyword.
- Lazy initialization.
- Simple and easy understand.
- Reflection attacks.
Enum Singleton class
public enum Singleton INSTANCE; // other methods >
The final clone method in Enum ensures that enum constants can never be cloned, and the special treatment by the serialization mechanism ensures that duplicate instances are never created as a result of deserialization. Reflective instantiation of enum types is prohibited. Together, these four things ensure that no instances of an enum type exist beyond those defined by the enum constants.
So, we allegedly get protection against serialization, clone and reflection attacks for free.
- Benefits and Drawbacks
- Benefits
- It is really concise.
- prevent serialization or reflection attacks.
- Drawbacks
- Do not have lazy initialization.
- Do not inherit from another base class, because enums can not extends another class. If we want to mimic inheritance, we might want to consider the interface mixin pattern in this New Java 8 “Object Support Mixin Pattern” for overriding Object.equals(), hashCode(), toString() and compareTo().
- Benefits
- Examples
- Comparator interface
- Website Designing
- Website Development
- Java Development
- PHP Development
- WordPress
- Graphic Designing
- Logo
- Digital Marketing
- On Page and Off Page SEO
- PPC
- Content Development
- Corporate Training
- Classroom and Online Training
- Data Entry
How to create singleton java
Learn Latest Tutorials
Preparation
Trending Technologies
B.Tech / MCA
Javatpoint Services
JavaTpoint offers too many high quality services. Mail us on h[email protected], to get more information about given services.
Training For College Campus
JavaTpoint offers college campus training on Core Java, Advance Java, .Net, Android, Hadoop, PHP, Web Technology and Python. Please mail your requirement at [email protected].
Duration: 1 week to 2 weekLike/Subscribe us for latest updates or newsletter
- Singleton on a Multiple Cores CPU In our Singleton class, we have a private static field called instance of type Singleton. It is just a pointer that will point to our only instance of the Singleton class. But the creation of this object is, in fact, a two step process.
- With public final field