Update singleton
This commit is contained in:
parent
ebcc857664
commit
9a2c5aa9aa
@ -13,13 +13,12 @@ tags:
|
|||||||
|
|
||||||
Ensure a class only has one instance, and provide a global point of access to it.
|
Ensure a class only has one instance, and provide a global point of access to it.
|
||||||
|
|
||||||
|
|
||||||
## Explanation
|
## Explanation
|
||||||
|
|
||||||
Real world example
|
Real-world example
|
||||||
|
|
||||||
> There can only be one ivory tower where the wizards study their magic. The same enchanted ivory
|
> There can only be one ivory tower where the wizards study their magic. The same enchanted ivory
|
||||||
> tower is always used by the wizards. Ivory tower here is singleton.
|
> tower is always used by the wizards. The ivory tower here is a singleton.
|
||||||
|
|
||||||
In plain words
|
In plain words
|
||||||
|
|
||||||
@ -48,7 +47,15 @@ Then in order to use:
|
|||||||
```java
|
```java
|
||||||
var enumIvoryTower1 = EnumIvoryTower.INSTANCE;
|
var enumIvoryTower1 = EnumIvoryTower.INSTANCE;
|
||||||
var enumIvoryTower2 = EnumIvoryTower.INSTANCE;
|
var enumIvoryTower2 = EnumIvoryTower.INSTANCE;
|
||||||
assertEquals(enumIvoryTower1, enumIvoryTower2); // true
|
LOGGER.info("enumIvoryTower1={}", enumIvoryTower1);
|
||||||
|
LOGGER.info("enumIvoryTower2={}", enumIvoryTower2);
|
||||||
|
```
|
||||||
|
|
||||||
|
The console output
|
||||||
|
|
||||||
|
```
|
||||||
|
enumIvoryTower1=com.iluwatar.singleton.EnumIvoryTower@1221555852
|
||||||
|
enumIvoryTower2=com.iluwatar.singleton.EnumIvoryTower@1221555852
|
||||||
```
|
```
|
||||||
|
|
||||||
## Class diagram
|
## Class diagram
|
||||||
@ -62,13 +69,13 @@ Use the Singleton pattern when
|
|||||||
* There must be exactly one instance of a class, and it must be accessible to clients from a well-known access point
|
* There must be exactly one instance of a class, and it must be accessible to clients from a well-known access point
|
||||||
* When the sole instance should be extensible by subclassing, and clients should be able to use an extended instance without modifying their code
|
* When the sole instance should be extensible by subclassing, and clients should be able to use an extended instance without modifying their code
|
||||||
|
|
||||||
## Typical Use Case
|
Some typical use cases for the Singleton
|
||||||
|
|
||||||
* The logging class
|
* The logging class
|
||||||
* Managing a connection to a database
|
* Managing a connection to a database
|
||||||
* File manager
|
* File manager
|
||||||
|
|
||||||
## Real world examples
|
## Known uses
|
||||||
|
|
||||||
* [java.lang.Runtime#getRuntime()](http://docs.oracle.com/javase/8/docs/api/java/lang/Runtime.html#getRuntime%28%29)
|
* [java.lang.Runtime#getRuntime()](http://docs.oracle.com/javase/8/docs/api/java/lang/Runtime.html#getRuntime%28%29)
|
||||||
* [java.awt.Desktop#getDesktop()](http://docs.oracle.com/javase/8/docs/api/java/awt/Desktop.html#getDesktop--)
|
* [java.awt.Desktop#getDesktop()](http://docs.oracle.com/javase/8/docs/api/java/awt/Desktop.html#getDesktop--)
|
||||||
@ -77,8 +84,8 @@ Use the Singleton pattern when
|
|||||||
|
|
||||||
## Consequences
|
## Consequences
|
||||||
|
|
||||||
* Violates Single Responsibility Principle (SRP) by controlling their own creation and lifecycle.
|
* Violates Single Responsibility Principle (SRP) by controlling their creation and lifecycle.
|
||||||
* Encourages using a global shared instance which prevents an object and resources used by this object from being deallocated.
|
* Encourages using a globally shared instance which prevents an object and resources used by this object from being deallocated.
|
||||||
* Creates tightly coupled code. The clients of the Singleton become difficult to test.
|
* Creates tightly coupled code. The clients of the Singleton become difficult to test.
|
||||||
* Makes it almost impossible to subclass a Singleton.
|
* Makes it almost impossible to subclass a Singleton.
|
||||||
|
|
||||||
|
@ -30,20 +30,20 @@ import lombok.extern.slf4j.Slf4j;
|
|||||||
* classloader instance and provides global access to it.</p>
|
* classloader instance and provides global access to it.</p>
|
||||||
*
|
*
|
||||||
* <p>One of the risks of this pattern is that bugs resulting from setting a singleton up in a
|
* <p>One of the risks of this pattern is that bugs resulting from setting a singleton up in a
|
||||||
* distributed environment can be tricky to debug, since it will work fine if you debug with a
|
* distributed environment can be tricky to debug since it will work fine if you debug with a
|
||||||
* single classloader. Additionally, these problems can crop up a while after the implementation of
|
* single classloader. Additionally, these problems can crop up a while after the implementation of
|
||||||
* a singleton, since they may start out synchronous and only become async with time, so it may
|
* a singleton, since they may start synchronous and only become async with time, so it may
|
||||||
* not be clear why you are seeing certain changes in behaviour.</p>
|
* not be clear why you are seeing certain changes in behavior.</p>
|
||||||
*
|
*
|
||||||
* <p>There are many ways to implement the Singleton. The first one is the eagerly initialized
|
* <p>There are many ways to implement the Singleton. The first one is the eagerly initialized
|
||||||
* instance in {@link IvoryTower}. Eager initialization implies that the implementation is thread
|
* instance in {@link IvoryTower}. Eager initialization implies that the implementation is thread
|
||||||
* safe. If you can afford giving up control of the instantiation moment, then this implementation
|
* safe. If you can afford to give up control of the instantiation moment, then this implementation
|
||||||
* will suit you fine.</p>
|
* will suit you fine.</p>
|
||||||
*
|
*
|
||||||
* <p>The other option to implement eagerly initialized Singleton is enum based Singleton. The
|
* <p>The other option to implement eagerly initialized Singleton is enum-based Singleton. The
|
||||||
* example is found in {@link EnumIvoryTower}. At first glance the code looks short and simple.
|
* example is found in {@link EnumIvoryTower}. At first glance, the code looks short and simple.
|
||||||
* However, you should be aware of the downsides including committing to implementation strategy,
|
* However, you should be aware of the downsides including committing to implementation strategy,
|
||||||
* extending the enum class, serializability and restrictions to coding. These are extensively
|
* extending the enum class, serializability, and restrictions to coding. These are extensively
|
||||||
* discussed in Stack Overflow: http://programmers.stackexchange.com/questions/179386/what-are-the-downsides-of-implementing
|
* discussed in Stack Overflow: http://programmers.stackexchange.com/questions/179386/what-are-the-downsides-of-implementing
|
||||||
* -a-singleton-with-javas-enum</p>
|
* -a-singleton-with-javas-enum</p>
|
||||||
*
|
*
|
||||||
@ -56,7 +56,7 @@ import lombok.extern.slf4j.Slf4j;
|
|||||||
* ThreadSafeLazyLoadedIvoryTower} since it doesn't synchronize the whole access method but only the
|
* ThreadSafeLazyLoadedIvoryTower} since it doesn't synchronize the whole access method but only the
|
||||||
* method internals on specific conditions.</p>
|
* method internals on specific conditions.</p>
|
||||||
*
|
*
|
||||||
* <p>Yet another way to implement thread safe lazily initialized Singleton can be found in
|
* <p>Yet another way to implement thread-safe lazily initialized Singleton can be found in
|
||||||
* {@link InitializingOnDemandHolderIdiom}. However, this implementation requires at least Java 8
|
* {@link InitializingOnDemandHolderIdiom}. However, this implementation requires at least Java 8
|
||||||
* API level to work.</p>
|
* API level to work.</p>
|
||||||
*/
|
*/
|
||||||
|
Loading…
x
Reference in New Issue
Block a user