Skip to content

Commit f01927d

Browse files
authored
Merge pull request #754 from abhijay94/Development
Added Singleton Design pattern implementation in Java and its test
2 parents e2a6b02 + 4a3f871 commit f01927d

File tree

2 files changed

+88
-0
lines changed

2 files changed

+88
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
package src.main.java.com.designpatterns.singletonpattern;
2+
3+
/**
4+
* The singleton pattern is a design pattern that restricts the instantiation of a class to one "single" instance.
5+
* This is useful when exactly one object is needed to coordinate actions across the system. The term comes from the
6+
* mathematical concept of a singleton.
7+
* <p>
8+
* The key idea in this pattern is to make the class itself responsible for controlling its instantiation (only once).
9+
* The hidden constructor (declared private) ensures that the class can never be instantiated from outside the class.
10+
* The public static operation can be accessed easily by using the class name and function name(Singleton.getInstance())
11+
*
12+
* @see <a href="https://en.wikipedia.org/wiki/Singleton_pattern">Singleton Pattern</a>
13+
*/
14+
public class Singleton {
15+
private volatile static Singleton instance = null;
16+
17+
private Singleton() {
18+
}
19+
20+
/**
21+
* A singleton implementation may use lazy initialization, where the instance is created when the static method
22+
* is first invoked.
23+
* <p>
24+
* If the static method might be called from multiple threads simultaneously, measures may need
25+
* to be taken to prevent race conditions that could result in the creation of multiple instances of the class.
26+
* <p>
27+
* The following implementation is a thread-safe sample implementation, using lazy initialization with
28+
* double-checked locking.
29+
*
30+
* @return the single instance of the Singleton class
31+
*/
32+
public static Singleton getInstance() {
33+
if (instance == null) {
34+
// First attempt to make thread safe
35+
synchronized (Singleton.class) {
36+
// Double Checked locking as multiple threads can reach the above step
37+
if (instance == null) {
38+
instance = new Singleton();
39+
}
40+
}
41+
}
42+
return instance;
43+
}
44+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
package src.test.java.com.designpatterns.singletonpattern;
2+
3+
import org.junit.Assert;
4+
import org.junit.Test;
5+
import src.main.java.com.designpatterns.singletonpattern.Singleton;
6+
7+
import java.util.ArrayList;
8+
import java.util.concurrent.ExecutorService;
9+
import java.util.concurrent.Executors;
10+
import java.util.concurrent.TimeUnit;
11+
12+
public class SingletonTest {
13+
private static volatile ArrayList<Integer> hashCodeList = new ArrayList<>();
14+
15+
@Test
16+
public void testSingleton() throws InterruptedException {
17+
boolean testFailed = false;
18+
ExecutorService es = Executors.newCachedThreadPool();
19+
// Creates 15 threads and makes all of them access the Singleton class
20+
// Saves the hash code of the object in a static list
21+
for (int i = 0; i < 15; i++)
22+
es.execute(() -> {
23+
try {
24+
Singleton singletonInstance = Singleton.getInstance();
25+
int singletonInsCode = singletonInstance.hashCode();
26+
hashCodeList.add(singletonInsCode);
27+
} catch (Exception e) {
28+
System.out.println("Exception is caught");
29+
}
30+
});
31+
es.shutdown();
32+
boolean finished = es.awaitTermination(1, TimeUnit.MINUTES);
33+
// wait for all threads to finish
34+
if (finished) {
35+
Integer firstCode = hashCodeList.get(0);
36+
for (Integer code : hashCodeList) {
37+
if (!firstCode.equals(code)) {
38+
testFailed = true;
39+
}
40+
}
41+
Assert.assertFalse(testFailed);
42+
}
43+
}
44+
}

0 commit comments

Comments
 (0)