Singleton is a creational design pattern, which ensures that only one object of its kind exists and provides a single point of access to it for any other code.
Singleton has almost the same pros and cons as global variables. Although they’re super-handy, they break the modularity of your code.
You can’t just use a class that depends on a Singleton in some other context, without carrying over the Singleton to the other context. Most of the time, this limitation comes up during the creation of unit tests.
Identification: Singleton can be recognized by a static creation method, which returns the same cached object.
Naïve Singleton (single-threaded)
It’s pretty easy to implement a sloppy Singleton. You just need to hide the constructor and implement a static creation method.
Singleton.java: Singleton
DemoSingleThread.java: Client code
OutputDemoSingleThread.txt: Execution result
Naïve Singleton (multithreaded)
The same class behaves incorrectly in a multithreaded environment. Multiple threads can call the creation method simultaneously and get several instances of Singleton class.
Singleton.java: Singleton
DemoMultiThread.java: Client code
OutputDemoMultiThread.txt: Execution result
Thread-safe Singleton with lazy loading
To fix the problem, you have to synchronize threads during first creation of the Singleton object.
Singleton.java: Singleton
DemoMultiThread.java: Client code
OutputDemoMultiThread.txt: Execution result
Want more?
There are even more special flavors of the Singleton pattern in Java. Take a look at this article to find out more: