裝飾器模式以及繼承的應用場景

    最近,看到有朋友在吐槽,說在用中間件的連接池的時候,得到的連接的實例,調用close方法之後,不能回到池裏面,而是真的關閉了連接。爲什麼大家會覺得調用close方法是回到連接池而不是關閉連接呢?這個還要從最常見的JDBC的連接池說起,幾乎常見的jdbc的連接池在構造連接的時候都增強了connection類,將其close方法重寫爲returnPool之類的,調用關閉即可回去連接池。

    

class PoolConnection implements Connection { 
	Connection conn;
	public PoolConnection(Connection conn,Pool<Connection> pool){
		this.conn = conn;
	}
	...
	@Override  
    public PreparedStatement prepareStatement(String sql) throws SQLException {  
        // TODO Auto-generated method stub  
        return conn.prepareStatement(sql);  
    }  
	@Override  
    public void close() throws SQLException {  
        //歸池
		pool.returnObject(this);
		
    }  
}
    可以看到,上述的增加的行爲是用裝飾器去實現的,這種實現,雖然會比較繁瑣(要實現接口所有的方法),好處也是顯而易見的,在沒有辦法手動初始化接口卻可以任意的在不改變接口的情況下,擴展我們的內部實現。回到最開始的,該中間件爲什麼調用close方法就沒有辦法close呢,很簡單,因爲它的連接池沒有針對該client的close方法去重寫或者是判斷是否是池化狀態。一般已經存在的中間件連接增加行爲的方式,又跟JDBC連接的有所不同,因爲我們知道怎麼去初始化一箇中間件的連接,且該連接只有一種實現(jdbc有多少種關係型數據庫就有多少種實現),所以,直接用繼承的方式就行了。

    總結下,什麼情況下用裝飾器什麼情況下用繼承呢?其實很簡單。有且只有一種實現,並且我們知道如何構造的時候(至少看得懂源碼),我們就可以用繼承去擴展。反之,類似於IO、JDBC,這種行爲我們只能夠用裝飾器去實現增加接口方法的行爲了。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章