DiContainer.QueueForInject
一旦构建了初始对象图,dicontainer.queueforinject将对给定的注入实例进行排队。
有时,有些实例不是由Zenject创建的,它们在启动时就已存在,并且您希望注入这些实例。在这些情况下,您通常会像这样将它们添加到容器中:
var foo = new Foo();
...
Container.Bind<Foo>().FromInstance(foo);
或者等价于:
Container.BindInstance(foo);
但是,使用FromInstance不会注入给定的实例。
一种可以立即在实例上注入的方法如下:
Container.BindInstance(foo);
Container.Inject(foo);
然而,这是不好的做法。不要在安装阶段实例化或插入,因为您要插入的对象可能需要绑定而这些绑定尚未被添加。
因此,处理这些情况的正确方法是使用QueueForInject:
Container.BindInstance(foo);
Container.QueueForInject(foo);
这样,在安装阶段之后,foo对象会在构建初始对象图的同时进行注入。
使用QueueForInject的另一个优点是Zenject将保证您的实例以正确的顺序注入。 换句话说,如果您有以下类:
class A
{
[Inject]
public void Init()
{
...
}
}
class B
{
[Inject]
public void Init(A a)
{
...
}
}
它们以下面的方式添加到安装器上:
var a = new A();
var b = new B();
Container.BindInstance(a);
Container.BindInstance(b);
Container.QueueForInject(a);
Container.QueueForInject(b);
这样,A将在B之前调用自身的注入方法,而与它们被添加到容器的顺序无关。 如果您在B的[Inject]方法中有一些初始化逻辑,并且需要提前初始化A,那么这种方式很好。
这也正是场景中初始MonoBehaviour的注入方式。 它们都是使用QueueForInject方法简单地添加到容器中的。
DiContainer Unbind / Rebind
可以将先前绑定语句中添加的绑定进行删除或替换。 但请注意,使用这些方法通常是不好的现象。
- Unbind - 从容器中删除所有与给定类型或标识匹配的绑定
Container.Bind<IFoo>().To<Foo>();
// 该句将使上面的绑定无效
Container.Unbind<IFoo>();
- Rebind - 重写已存在的绑定,相当于调用给定类型的Unbind方法然后再调用bind方法
Container.Bind<IFoo>().To<Foo>();
Container.Rebind<IFoo>().To<Bar>();
其他DiContainer方法
- DiContainer.ParentContainers - 给定DiContainer的父容器。 例如,对于与SceneContext关联的DiContainer,其父容器通常是与ProjectContext关联的DiContainer(除非您使用了Scene Parenting,在这种情况下其父容器是另一个SceneContext)
- DiContainer.IsValidating - 如果是再验证模式下运行该容器,则返回true。 这在需要在验证步骤中添加特殊逻辑的某些不常见的情况下非常有用。
- DiContainer.CreateSubContainer - 创建一个新容器作为当前容器的子容器。 这可能对涉及创建具有复杂的依赖关系的对象的自定义工厂很有用。 例如:
var subContainer = Container.CreateSubContainer();
subContainer.Bind<Foo>();
subContainer.Bind<Bar>();
subContainer.Bind<Qux>();
var foo = subContainer.Resolve<Foo>();
- DiContainer.HasBinding - 如果已添加了与给定类型或标识匹配的绑定,则返回true。 如果要避免重复添加可能已在先前安装程序中添加的绑定,这可能很有用
if (!Container.HasBinding<IFoo>())
{
Container.Bind<IFoo>().To<Foo>().AsSingle();
}
- DiContainer.GetDependencyContracts - 返回给定类型所依赖的所有类型的列表。 这可能很有用,例如,如果您想对项目进行一些静态分析,或者您想自动生成依赖关系图等。
网友评论