我想知道如何使用DI管理对象。假设我有一个班级
class Foo : IFoo, IDisposable
{
// ...
}
然后将这个类注入另一个类
class Bar
{
public Bar(IFoo foo)
{
this.Foo = foo
}
IFoo Foo { get; set; }
}
然后我在某个范围内绑定它(我的例子使用MVC和Ninject)
this.Bind<IFoo>().To<Foo>().InRequestScope();
我想知道,因为依赖注入框架处理Foo
的生命周期,我应该在Bar
中实现IDispoable吗?我的想法是DI正在管理Foo
的生命周期,所以如果其他类使用Foo
,请不要触摸它。此外,由于一次性对象作为构造函数参数传递到Bar
,Bar
不会换行一次性对象,因此它不知道{的调用者如何{1}}想要在Bar
垃圾收集后使用Foo
。这是对的吗?
答案 0 :(得分:3)
是的,您的假设是正确的。 Ninject会为你处理这个物体。
答案 1 :(得分:3)
这是管理生命周期的一般问题。基本规则是创建对象的人拥有该实例的所有权。所有者应该处置/销毁该实例。所有权可以传递给其他人,这使得“其他人”负责销毁该实例。
在您的情况下,Foo实例不是由Bar创建的,因此bar不负责处理该实例。由于Ninject为您创建了该实例,因此它负责清理它。
可以传递所有权,但这必须是明确的。显式所有权传递的一个很好的例子是工厂设计模式:
IFoo CreateNewFoo();
虽然此方法会创建新的IFoo
实例,但很明显他将所有权传递给调用者。
传递所有权的BAD方式的一个很好的例子是.NET的StreamReader
类。它在构造函数中需要一个一次性对象,但它需要所有权。虽然文档声明该类处理给定的对象,但这种行为使许多开发人员感到困惑,因为它违反了一般的所有权规则。微软最终通过添加一个允许抑制给定流处理的ctor重载来解决这个问题。