關於spring的IOC和DI,網路上有各種不同的文章可供閱讀,但很多都是轉載或者是“淺談”,至少我看了好幾篇被轉的昏頭昏腦。然後我直接看spring-framework-5文件,知道了給ioc和DI最早定義或者介紹的文章(至少我看到的是最早的了)
IoC容器和Dependency Injection模式 - Martin Fowler
講解的十分透徹。這裡我就做個隨筆。
IOC和DI的區別
控制反轉:將控制權反轉(轉交)給其他元件。
依賴注入:將介面的具體實現通過介面卡或者容器注入給介面的呼叫方。
依賴注入實現的同時也達成了控制反轉,因為它將對介面實現類的選擇權交給了容器而不是主程式。所以Martin Fowler使用依賴注入來表示這個模式。
在我的理解中,依賴注入一定具有控制反轉,但是控制反轉不一定實現了依賴注入。 Martin Fowler也給出了例子:
在視覺化頁面的表單輸入中,表單的校驗如果從頁面的程式碼進行校驗交給校驗元件。那麼這就將校驗的控制權反轉給了元件或者框架。但是這個過程並沒有實現依賴注入。
依賴注入與策略設計模式的思考
根據Martin Fowler的文章瞭解依賴注入的結構後發現它有點像策略設計模式。
策略設計模式:通過傳入不同的引數來使用或者獲取介面的不同實現
感覺和DI有點像,但仔細思考後發現兩者還是有許多區別的。
首先是對介面的不同實現。策略設計的一個要求就是介面的不同實現都要在本地或者更加準確的說要在主程式中。但是隨著專案越來越大業務功能越來越多,分工完成不同的業務實現是當前的主流。因此介面的實現就不一定在主程式中了。
而且如果用介面卡來組合介面的不同實現和主程式,那麼每次新增新的元件或者更換元件的時候都要在主程式中修改程式碼,這是十分麻煩的。
因此,使用一個通用的介面卡或者說容器來管理所有的介面和對應的實現,如果要加入新的元件,只需要往容器中註冊對應的介面類和它的實現。當主程式要使用或者擴充套件功能的時候只需要往容器中請求對應的介面就可以輕鬆的獲取到該實現了。當第三方對這個元件有更加完善的實現的時候,只需要在容器中修改介面繫結的實現就可以輕鬆替換舊的元件。這種主程式-容器-元件完全分離的形式使得程式編寫就像搭積木一樣,通過獲取不同的元件就能搭建出全新的應用功能。