1. 程式人生 > >Sping三種注入方式

Sping三種注入方式

Sping三種注入方式

                                                                       (本文摘自夏昕:開發指南)

依賴注入的三種實現形式

我們將元件的依賴關係由容器實現,那麼容器如何知道一個元件依賴哪些其它的元件呢?這些回撥方法會告知容器它所依賴的元件。根據回撥方法的不同,我們可以將IoC分為三種形式:

1、 介面注入

 簡單的說,介面注入就是在執行期,載入介面實現並建立其例項的工作由容器完成。

如下面這個類:

public class ClassA {

private InterfaceB clzB;

   public Object doSomething(InterfaceB b) {

     clzB = b;

      return clzB.doIt();

    }

 ……

}

在執行期,InterfaceB例項將由容器提供。

Type1IOC發展較早(有意或無意) ,在實際中得到了普遍應用,即使在IOC的概念尚未確立時,這樣的

方法也已經頻繁出現在我們的程式碼中。

下面的程式碼大家應該非常熟悉:

public class MyServlet extends HttpServlet {

 public void doGet(

HttpServletRequest request, 

HttpServletResponse response)

     throws ServletException, IOException {

   ……

 }

}   SpringFrameWork Developer’s Guide Version 0.6

這也是一個Type1 型注入,HttpServletRequestHttpServletResponse例項由Servlet Container

在執行期動態注入。

另,Apache Avalon是一個較為典型的Type1IOC容器。

2、 設定注入

在各種型別的依賴注入模式中,設值注入模式在實際開發中得到了最廣泛的應用(其中很大一部分得力於

Spring框架的影響)。

基於設定模式的依賴注入機制更加直觀、也更加自然。前面的使用者註冊示例,就是典

型的設定注入,即通過類的setter方法完成依賴關係的設定。

3、 構造子函式注入

Type3 構造子注入

 構造子注入,即通過建構函式完成依賴關係的設定,如:

public class DIByConstructor {

   private final DataSource dataSource;

   private final String message;

   public DIByConstructor(DataSource ds, String msg) {

     this.dataSource = ds;

     this.message = msg;

    }

 ……

}

 可以看到,在Type3型別的依賴注入機制中,依賴關係是通過類建構函式建立,容器通過呼叫類的構

造方法,將其所需的依賴關係注入其中。

 PicoContainer (另一種實現了依賴注入模式的輕量級容器) 首先實現了Type3型別的依賴注入模式

.幾種依賴注入模式的對比總結

介面注入模式因為歷史較為悠久,在很多容器中都已經得到應用。但由於其在靈活性、易用性上不如其他兩種注入模式,因而在IOC的專題世界內並不被看好。

Type2Type3型的依賴注入實現則是目前主流的IOC實現模式。這兩種實現方式各有特點,也各具優勢(一句經典廢話) 

 Type2 設值注入的優勢

1 對於習慣了傳統JavaBean開發的程式設計師而言,通過setter方法設定依賴關係顯得更加直

觀,更加自然。

2 如果依賴關係(或繼承關係)較為複雜,那麼Type3模式的建構函式也會相當龐大(我們需

要在建構函式中設定所有依賴關係) ,此時Type2模式往往更為簡潔。

3 對於某些第三方類庫而言,可能要求我們的元件必須提供一個預設的建構函式(如Struts

中的Action ,此時Type3型別的依賴注入機制就體現出其侷限性,難以完成我們期望的功

能。

Type3 構造子注入的優勢:

1 “在構造期即建立一個完整、合法的物件” ,對於這條Java設計原則,Type3無疑是最好的

響應者。

2 避免了繁瑣的setter方法的編寫,所有依賴關係均在建構函式中設定,依賴關係集中呈現,

更加易讀。

3 由於沒有setter方法,依賴關係在構造時由容器一次性設定,因此元件在被建立之後即處於

相對“不變”的穩定狀態,無需擔心上層程式碼在呼叫過程中執行setter方法對元件依賴關係

產生破壞,特別是對於Singleton模式的元件而言,這可能對整個系統產生重大的影響。

4 同樣,由於關聯關係僅在建構函式中表達,只有元件建立者需要關心元件內部的依賴關係。

對呼叫者而言,元件中的依賴關係處於黑盒之中。對上層遮蔽不必要的資訊,也為系統的

層次清晰性提供了保證。

5 通過構造子注入,意味著我們可以在建構函式中決定依賴關係的注入順序,對於一個大量

依賴外部服務的元件而言,依賴關係的獲得順序可能非常重要,比如某個依賴關係注入的

先決條件是元件的DataSource及相關資源已經被設定。

可見,Type3Type2模式各有千秋,而SpringPicoContainer都對Type3Type2型別的依賴注入機制提供了良好支援。這也就為我們提供了更多的選擇餘地。理論上,以Type3型別為主,輔之以Type2型別機制作為補充,可以達到最好的依賴注入效果,不過對於基於Spring Framework開發的應用而言,Type2使用更加廣泛。