IObjectFactory本质上是一个注册了各种对象及其依赖项的高级工厂。通过IObjectFactory接口,可以读取容器内的对象定义并访问它们所代表的对象。如果只需要使用IOjbectFactory接口的功能,可以用代码创建其实现类的实例,然后读取XML对象定义中的内容,如下:
[C#] IResource input = new FileSystemResource ("objects.xml"); XmlObjectFactory factory = new XmlObjectFactory(input);
对象工厂创建之后,就可以使用GetObject(string)方法(或者使用索引器factory[string],更为简洁)获取需要的对象:
[C#] object foo = factory.GetObject ("foo"); // gets the object defined as 'foo' object bar = factory ["bar"]; // same thing, just using the indexer
上面的代码执行后,如果对象以singleton方式(默认的方式)定义,就会获得该对象一个唯一的引用;如果对象定义中singleton属性为false,那么就每次调用这段代码都会返回一个新的对象:
<object id="exampleObject" type="Examples.ExampleObject, ExamplesLibrary"/> <object id="anotherObject" type="Examples.ExampleObject, ExamplesLibrary" singleton="false"/>
[C#] object one = factory ["exampleObject"]; // gets the object defined as 'exampleObject' object two = factory ["exampleObject"]; Console.WriteLine (one == two) // prints 'true' object three = factory ["anotherObject"]; // gets the object defined as 'anotherObject' object four = factory ["anotherObject"]; Console.WriteLine (three == four); // prints 'false'
对客户代码而言,IObjectFactory的使用非常简单,只需要用到其中的7个方法(或索引器),如下:
bool ContainsObject(string):如果IObjectFactory包含以某个名称命名的对象,则返回true。
object GetObject(string):返回以指定名称命名的对象。根据对象的配置方式,可能返回一个singleton对象(共享的),也可能返回一个新创建的对象。如果请求的对象没有找到,就会抛出NoSuchObjectDefinitionException异常,如果在初始化和准备对象时出错,则抛出ObjectsException异常。
Object this[string]:IObjectFactory接口定义的索引器。工作方式同GetObject(string)方法一样。本文一般都使用GetObject(string)方法,不过要注意只要能使用GetObject(string)方法的地方就可以使用索引器。
Object GetObject(string,Type):返回以给定名称注册的对象,并转换为指定的类型。若无法进行转型,会抛出ObjectNotOfRequiredTypeException异常。此外,GetObject(string)遵守的规则也适用于该方法。
bool IsSingleton(string):判断以给定名称命名的对象是singleton还是prototype。如果找不到所请求的对象,会抛出NoSuchObjectDefinitionException异常。
string[] GetAliases(string):返回以给定名称命名的对象的别名(如果该对象定义了别名的话)。
void ConfigureObject(object target):以容器中某个抽象对象定义为模板,为目标对象进行依赖注入。要注意的是,在用作模板的抽象对象定义中,类型不能省略,且必须和目标对象的类型全名完全一致(按:是否包含程序集名均可;因为指定了类型,所以一定要显式使用abstract属性;此外,该抽象对象定义不能以任何方式(id或name)配置标识符;原文对此描述不准确,读者可以自行实验)。如果对象的创建和初始化不受开发人员的控制,比如ASP.NET创建的Web控件、或者WinForm程序创建的用户控件,就可以用这种方式对其进行依赖注入。
void ConfigureObject(object target, string name):功能与上面的方法一样,不同是,这次是按照某个指定名称的对象定义为模板,为目标对象进行依赖注入。(按:注意,此时以name为名的对象定义不必是抽象的,并且在类型上可以和目标对象完全不一致,但其依赖项必须兼容)。