【讀書筆記 - Effective Java】03. 用私有構造器或者枚舉類型強化Singleton屬性

實現Singleton(表明本質上惟一的系統組件)的三種方法:性能

1. 保持私有構造器,導出公有的靜態成員,客戶端訪問該類的惟一實例。spa

2. 保持私有構造器,公有的成員是靜態工廠方法。code

3. 單元素的枚舉類型已經成爲實現Singleton的最佳方法對象

 

前兩種方法有兩點注意:blog

1. 享有特權的客戶端能夠經過反射機制調用私有構造器。若是須要抵禦這種攻擊,能夠修改構造器,讓它在被要求建立第二個實例的時候拋出異常。get

2. 若是要使其變成可序列化的,須要:class

(1) implement Serializable;序列化

(2) 聲明全部實例域是瞬時(transient)的;引用

(3) 提供一個返回惟一實例instance的readResolve方法(由於每次反序列化一個序列化的實例時,都會建立一個新的實例)。反射

 

示例1:公有域——性能沒有優點,可是組成類的成員聲明清楚代表這是一個單例類。公有靜態域是final的,老是包含相同的對象引用。

public class Elvis {
    public static final Elvis instance = new Elvis();
    private Elvis() { }
    // method...
}

 

示例2:靜態工廠方法——提供了靈活性,改變是不是單例類。可是很容易被修改。

public class Elvis {
    private static final Elvis instance = new Elvis();
    private Elvis() { }
    public static Elvis getInstance() {
        return instance;
    }
    // method...
}

 

示例3:單元素枚舉——與公有域方法相近,但沒有前面說的兩個注意。無償提供了序列化機制,絕對防止屢次實例化。

public enum Elvis {
    instance;
    // method...
}
相關文章
相關標籤/搜索