還記得不少年前,面試就讓在白板上寫個單例模式,當時技術渣渣,還寫的是class A.面試官還說,你就不能寫個Singleton.java
單例模式:即某個類在整個系統中只有一個實例對象可被獲取和使用的代碼模式面試
(1) 直接實例化餓漢式編程
/** * 餓漢式(直接建立實例對象) * 直接經過類名調用 * * @author kevin * @date 2019/7/8 11:23 */ public class Singleton1 { public static final Singleton1 INSTANCE = new Singleton1(); private Singleton1() { } }
(2)枚舉式設計模式
/** * 餓漢式(枚舉) * * @author kevin * @date 2019/7/8 11:29 */ public enum Singleton2 { INSTANCE; }
(3) 靜態代碼塊安全
import java.io.IOException; import java.util.Properties; /** * @author kevin * @date 2019/7/8 13:35 */ public class Singleton3 { public static final Singleton3 INSTANCE; private String info; static { try { Properties properties = new Properties(); properties.load(Singleton3.class.getClassLoader().getResourceAsStream("sing.properties")); INSTANCE = new Singleton3(properties.getProperty("info")); } catch (IOException e) { throw new RuntimeException(e); } } private Singleton3(String info) { this.info = info; } public String getInfo() { return info; } public void setInfo(String info) { this.info = info; } @Override public String toString() { return "Singleton3{" + "info='" + info + '\'' + '}'; } }
注意:這裏還有個properties文件多線程
info=kevin
測試ide
Singleton3 s = Singleton3.INSTANCE; System.out.println(s);
結果函數
Singleton3{info='kevin'}
(1)線程不安全測試
public class Singleton4 { private static Singleton4 instance; public static Singleton4 getInstance(){ if(instance == null){ instance = new Singleton4(); } return instance; } private Singleton4(){ } }
(2) 線程安全this
/** * @author kevin * @date 2019/7/8 13:56 */ public class Singleton5 { private static Singleton5 instance; public static Singleton5 getInstance() { if (instance == null) { synchronized (Singleton5.class) { if (instance == null) { instance = new Singleton5(); } } } return instance; } private Singleton5() { } }
(3)靜態內部類 線程安全
/** * 靜態內部類不會自動隨着外部類的加載而初始化 * * @author kevin * @date 2019/7/8 13:56 */ public class Singleton6 { private static class Inner { private static final Singleton6 INSTANCE = new Singleton6(); } public static Singleton6 getInstance() { return Inner.INSTANCE; } private Singleton6() { } }
注意:靜態內部類不會自動隨着外部類的加載而初始化
好了,玩的開心。