1. 什麼是 IoC ?
關于IoC的詳細解釋請看 Inversion of Control Containers and the Dependency Injection pattern (英文/中文),本文隻會作一些簡單介紹
IoC(Inversion of Control),我們叫它"控制反轉",也可以叫它"依賴注入"(Dependency Injection)。
引用自 JGTM'2004 [MVP] 的話來解釋IoC
>>> 原來我是這樣解釋應用IoC的意圖和方式的(但還是不夠清晰):如果我想打破A->B的依賴,那麼我可以通過引入A、B之間的互動協定I來辦到,也 就是将A->B變為(A->I)+(I<-B)(此舉同時滿足了DIP和OCP原則),那麼IoC就是幫助我們用各種各樣的方法(如構 造器注入、屬性注入或接口注入等等)在運作期把I的一個具體實作B傳達給A使用的一系列機制。
使用IoC的主要目地就是實作程式子產品的低偶合,在DotNet下比較著名的IoC架構是Castle和Spring.net。
2. IoC的三種形式
依賴注入的形式主要有三種,我分别将它們叫做構造子注入(Constructor Injection)、設值方法注入(Setter Injection)和接口注入(Interface Injection)。
3. Castle中的IoC介紹
Castle.IoC 支援構造子注入和設值方法注入,但更側重構造子注入。
4. 使用Castle.IoC
使用 Castle.IoC 主要是配置 components
4.1 使用代碼配置
public static WindsorContainer container = new WindsorContainer( @" ../../config.xml " );
container.AddComponent( " FormatService " , typeof (FormatService) );
container.AddComponent( " format " , typeof (IMessageFormat), typeof (HtmlMessage) );
4.2 使用XML檔案配置
<? xml version="1.0" encoding="utf-8" ?>
< castle >
< components >
< component id ="FormatService"
type ="IoCSample.FormatService,IoCSample" />
< component id ="format"
service ="IoCSample.Components.IMessageFormat,IoCSample"
type ="IoCSample.Components.HtmlMessage,IoCSample" />
</ components >
</ castle >
如何配置IList,IDictionary,Array等複雜類型
IDictionary
代碼:
public class C
{
public C()
{}
public C(IDictionary d)
{
this.dictionary=d;
}
private IDictionary dictionary;
public IDictionary Dictionary
{
get
{return this.dictionary;}
}
} 配置:
< component id ="c" type ="CastleDemo.C,CastleDemo" >
< parameters >
< d >
< item keyType ="System.String" valueType ="System.String" >
< item key ="a" > a </ item >
< item key ="b" > b </ item >
</ item >
</ d >
</ parameters >
</ component >
IList
代碼:
public class D
{
private IList list;
public D()
{}
public IList List
{
get
{return this.list;}
}
public D(IList list)
{
this.list=list;
}
} 配置:
< component id ="d" type ="CastleDemo.D,CastleDemo" >
< parameters >
< list >
< item type ="System.String" >
< item > a </ item >
< item > b </ item >
< item > c </ item >
</ item >
</ list >
</ parameters >
</ component >
Array
代碼:
public class E
{
private int[] ages;
public int[] Ages
{
get
{return this.ages;}
}
public E()
{
}
public E(int[] ages)
{
this.ages=ages;
}
} 配置:
< component id ="e" type ="CastleDemo.E,CastleDemo" >
< parameters >
< ages >
< item type ="System.Int32" >
< item > 1 </ item >
< item > 2 </ item >
< item > 3 </ item >
</ item >
</ ages >
</ parameters >
</ component >