天天看點

我對IoC/DI的了解

IoC

IoC :   Inversion of Control ,控制反轉,  控制權從應用程式轉移到架構(如 IoC 容器),是架構共有特性

1、為什麼需要IoC容器 1.1、應用程式主動控制對象的執行個體化及依賴裝配 

A a = new AImpl();
B b = new BImpl();
a.setB(b);
           

本質:建立對象,主動執行個體化,直接擷取依賴,主動裝配  缺點:更換實作需要重新編譯源代碼            很難更換實作、難于測試            耦合執行個體生産者和執行個體消費者 

A a = AFactory.createA();
B b = BFactory.createB();
a.setB(b);
           

  本質:建立對象,被動執行個體化,間接擷取依賴,主動裝配  (簡單工廠)  缺點:更換實作需要重新編譯源代碼            很難更換實作、難于測試

A a = Factory.create(“a”);
B b = Factory.create(“b”);
a.setB(b); 
           

  <!—配置.properties-->

a=AImpl
b=BImpl
      

  本質:建立對象,被動執行個體化,間接擷取依賴, 主動裝配         (工廠 +反射 +properties配置檔案、            Service Locator、系統資料庫)  缺點:備援的依賴裝配邏輯

我想直接:     //傳回裝配好的a

A a = Factory.create(“a”); 
           

               1.2、可配置通用工廠:工廠主動控制,應用程式被動接受,控制權從應用程式轉移到工廠

//傳回裝配好的a 
A a = Factory.create(“a”);
           

   <!—配置檔案-->

<bean id=“a” class=“AImpl”>
    <property name=“b” ref=“b”/>
</bean>
<bean id=“b” class=“BImpl”/>
           

 本質:建立對象和裝配對象,            被動執行個體化,被動接受依賴,被動裝配         (工廠 +反射 +xml配置檔案) 缺點:不通用

步驟: 1、讀取配置檔案根據配置檔案通過反射 建立 AImpl 2、發現 A需要一個類型為 B的屬性 b 3、到工廠中找名為 b的對象,發現沒有,讀取 配置檔案通過反射建立 BImpl 4、将 b對象裝配到 a對象的 b屬性上 【元件的配置與使用分離開(解耦、更改實作無需修改源代碼、易于更好實作) 】

1.3、 IoC(控制反轉)容器:容器主動控制

//傳回裝配好的a 
A a = ApplicationContext.getBean(“a”);
           

 <!—配置檔案-->

<bean id=“a” class=“AImpl”>
    <property name=“b” ref=“b”/>
</bean>
<bean id=“b” class=“BImpl”/>
           

  本質:建立對象和裝配對象、管理對象生命周期           被動執行個體化,被動接受依賴,被動裝配         (工廠 +反射 +xml配置檔案) 通用 

我對IoC/DI的了解

IoC 容器:實作了 IoC 思想的容器就是 IoC 容器

2、IoC容器特點 【 1 】無需主動 new對象;而是描述對象應該如何被建立即可           IoC 容器幫你建立,即被動執行個體化; 【 2 】不需要主動裝配對象之間的依賴關系,而是描述需要哪個服務(元件),          IoC 容器會幫你裝配(即負責将它們關聯在一起),被動接受裝配; 【 3 】主動變被動,好萊塢法則:别打電話給我們,我們會打給你; 【 4 】迪米特法則(最少知識原則):不知道依賴的具體實作,隻知道需要提供某類服務的對象(面向抽象程式設計),松散耦合,一個對象應當對其他對象有盡可能少的了解 ,不和陌生人(實作)說話 【 5 】 IoC是一種讓服務消費者不直接依賴于服務提供者的元件設計方式,是一種減少類與類之間依賴的設計原則。

3、了解IoC容器問題關鍵:控制的哪些方面被反轉了? 1、誰控制誰?為什麼叫反轉? ------  IoC 容器控制,而以前是應用程式控制,是以叫反轉  2、控制什麼?               ------  控制應用程式所需要的資源(對象、檔案 …… ) 3、為什麼控制?             ------  解耦元件之間的關系  4、控制的哪些方面被反轉了? ------  程式的控制權發生了反轉:從應用程式轉移到了 IoC 容器。 

思考:     1: IoC/DI等同于工廠嗎?     2: IoC/DI跟以前的方式有什麼不一樣? 領會: 主從換位的思想

我對IoC/DI的了解

4、實作了IoC思想的容器就是輕量級容器嗎? 如果僅僅因為使用了控制反轉就認為這些輕量級容器與衆不同,就好象在說我的轎車與衆不同因為它有四個輪子? 

容器:提供元件運作環境,管理元件聲明周期(不管元件如何建立的以及元件之間關系如何裝配的);

IoC容器不僅僅具有容器的功能,而且還具有一些其他特性---如依賴裝配               控制反轉概念太廣泛,讓人迷惑,後來 Martin   Fowler  提出依賴注入概念 Martin   Fowler   Inversion of Control Containers and the Dependency Injection pattern   http://martinfowler.com/articles/injection.html

DI

2、什麼是DI DI :依賴注入( Dependency Injection )   :用一個單獨的對象(裝配器)來 裝配對象之間的依賴關系   。

我對IoC/DI的了解

2、了解DI問題關鍵 誰依賴于誰?           -------    應用程式依賴于 IoC 容器 為什麼需要依賴?        -------    應用程式依賴于 IoC 容器裝配類之間的關系 依賴什麼東西?          -------    依賴了 IoC 容器的裝配功能 誰注入于誰?            -------    IoC 容器注入應用程式 注入什麼東西?          -------    注入應用程式需要的資源(類之間的關系)  

更能描述容器其特點的名字 ——“依賴注入”( Dependency Injection) IoC容器應該具有依賴注入功能,是以也可以叫 DI容器 

3、DI優點      【 1 】幫你看清元件之間的依賴關系,隻需要觀察依賴注入的機制( setter/構造器),就可以掌握整個依賴(類與類之間的關系)。      【 2 】元件之間的依賴關系由容器在運作期決定,形象的來說,即由容器動态的将某種依賴關系注入到元件之中。      【 3 】依賴注入的目标并非為軟體系統帶來更多的功能,而是為了提升元件重用的機率,并為系統搭建一個靈活、可擴充的平台。通過依賴注入機制,我們隻需要通過簡單的配置,而無需任何代碼就可指定目标需要的資源,完成自身的業務邏輯,而不用關心具體的資源來自何處、由誰實作。

使用 DI 限制:元件和裝配器( IoC容器)之間不會有依賴關系,是以元件無法從裝配器那裡獲得更多服務,隻能獲得配置資訊中所提供的那些。 

4、實作方式    1、構造器注入    2、 setter注入    3、接口注入:在接口中定義需要注入的資訊,并通過接口完成注入        @Autowired        public void prepare(MovieCatalog movieCatalog,            CustomerPreferenceDao customerPreferenceDao) {            this.movieCatalog = movieCatalog;            this.customerPreferenceDao = customerPreferenceDao;        }

使用IoC/DI容器開發需要改變的思路 1、應用程式不主動建立對象,但要描述建立它們的方式。 2、在應用程式代碼中不直接進行服務的裝配,但要配置檔案中描述哪一個元件需要哪一項服務。容器負責将這些裝配在一起。

其原理是基于 OO設計原則的 The Hollywood Principle: Don‘t call us, we’ll call you(别找我,我會來找你的)。也就是說,所有的元件都是被動的( Passive),所有的元件初始化和裝配都由容器負責。元件處在一個容器當中,由容器負責管理。

IoC 容器功能:執行個體化、初始化元件、裝配元件依賴關系、負責元件生命周期管理。

本質:       IoC:控制權的轉移,由應用程式轉移到架構;       IoC/DI容器: 由應用程式主動執行個體化對象 變被動等待對象(被動執行個體化);       DI:  由專門的裝配器裝配元件之間的關系;       IoC/DI容器: 由應用程式主動裝配對象的依賴 變應用程式被動接受依賴

關于IoC/DI與DIP之間的關系 詳見 http://www.iteye.com/topic/1122310?page=5#2335746

IoC/DI與迪米特法則 詳見http://www.iteye.com/topic/1122310?page=5#2335748

繼續閱讀