單例模式的定義
個人理解,單例是指單個實例,在整個應用程序當中有且僅有一個實例存在,該實例是通過代碼指定好的(自行創建的)。
為什么要使用
- 解決在高並發過程中,多個實例出現邏輯錯誤的情況。
- 在特定的業務場景下避免對象重復創建,節約內存。
實現的兩種方式
餓漢式
顧名思義,不管有沒有使用到該對象,只要程序啟動成功,該單實例對象就存在。
代碼如下:
/**
* 餓漢式
*/
public class SingletonHungry {
private static SingletonHungry instance = new SingletonHungry();
public static SingletonHungry instance(){
return instance;
}
public static void main(String[] args) {
SingletonHungry instance1 = SingletonHungry.instance();
SingletonHungry instance2 = SingletonHungry.instance();
System.out.println(instance1);
System.out.println(instance2);
}
}
上述情況,滿足在單線程和多線程中使用。
懶漢式
顧名思義,只有在程序當中使用到該對象的時候,該單實例對象才會被實例化。
代碼如下:
/**
* 懶漢式-單線程
*/
public class SingletonLazy {
public static SingletonLazy instance = null ;
public static SingletonLazy instance() {
if(instance == null) {
instance = new SingletonLazy() ;
}
return instance ;
}
}
上述編寫的代碼中,乍一看,沒問題,滿足了單實例對象。可是細細一琢磨,咋感覺這不對,如果多線程情況下,就很難保證單實例對象了。下面提供一種多線程情況下實現單例的方式:
/**
* 懶漢式-多線程
*/
public class SingletonLazy {
public static SingletonLazy instance = null ;
public static SingletonLazy instance() {
if(instance == null ) {
synchronized (SingletonLazy.class) {
if(instance == null) {
instance = new SingletonLazy();
}
}
}
return instance ;
}
}
上述的代碼中滿足了多線程的使用場景,就是使用了上鎖+雙重檢查來進行實現。
歡迎交流!