我在Unity中尝试以下内容:
我有一个带有以下构造函数的类型
public Type1(Type2 firstDependency, Type3 secondDependency)
使用Unity解析Type1
时,我想指定要注入的Type2
的特定实例。 Type2
的此特定实例未在容器中注册。 Type3
已在容器中注册,应照常解决。
更具体地说,请考虑Type1
是DocumentViewer
类。 Type2
是具体的Document
。 Type3
是SpellingChecker
。
我希望能够解析DocumentViewer
只能在运行时知道的Document
。可以创建多个DocumentViewer
个不同Documents
的实例。
我该怎么做?
答案 0 :(得分:2)
这是我做的一个简单示例,您使用RegisterInstance或者您可以使用Lifetime管理Claas
static void Main(string[] args)
{
IUnityContainer container = new UnityContainer();
container.RegisterType<Type1>();
container.RegisterInstance<Type2>(new Type2());
Type1 t = container.Resolve<Type1>();
Type2 t2 = container.Resolve<Type2>();
Type3 t3 = container.Resolve<Type3>();
Console.ReadKey();
}
public class Type1
{
}
public class Type2
{
}
public class Type3
{
private Type1 t;
private Type2 t2;
public Type3(Type1 t, Type2 t2)
{
this.t = t;
this.t2 = t2;
}
}
更新:我在构造函数中包含了一个带有两个参数的类型,以表明它也可以解析。
答案 1 :(得分:0)
我不想在原始容器中注册Type2的实例。对于Type1的不同实例,type2的实例可以是不同的。
我的下一步尝试是创建一个子容器,并在那里注册Type2的特定实例。
答案 2 :(得分:0)
尝试使用命名实例:
IUnityContainer container = new UnityContainer();
container.RegisterType<Type1>();
container.RegisterType<Type2>("Instance 1", new ContainerControlledLifetimeManager());
container.RegisterType<Type2>("Instance 2", new ContainerControlledLifetimeManager());
container.RegisterType<Type3>();
Type1 type1 = container.Resolve<Type1>();
if (type1 == ...)
{
Type2 instance1 = container.Resolve<Type2>("Instance 1");
}
else
{
Type2 instance2 = ontainer.Resolve<Type2>("Instance 2");
}
您可以对类型1进行一些检查,并确定您需要哪种类型2的实例。请注意,“new ContainerControlledLifetimeManager()”参数将初始化抵制类型的单例实例,因此您将始终获得类型2的相同实例。
更新:与界面相同。希望这会有所帮助。
IUnityContainer container = new UnityContainer();
container.RegisterType<TextDocument>();
container.RegisterType<ImageDocument>();
container.RegisterType(typeof (IView), typeof (TextView), "Text", new ContainerControlledLifetimeManager());
container.RegisterType(typeof (IView), typeof (ImageView), "Image", new ContainerControlledLifetimeManager());
IDocument document = container.Resolve<TextDocument>();
IView view = null;
if (document is TextDocument)
{
view = container.Resolve<IView>("Text");
}
else
{
view = container.Resolve<IView>("Image");
}
view.Show();
答案 3 :(得分:0)
如果您有一个具有多个构造函数的类,则可以使用“InjectionConstructor”属性决定Unity容器使用哪个构造函数。这使您可以手动设置一些参数。
public class Test
{
public Test()
{
}
// Always use the following constructor
[InjectionConstructor]
public Test(Type1 type1) : this()
{
}
public Test(Type1 type1, Type2 type2) : this(type1)
{
}
}
答案 4 :(得分:0)
使用工厂。
public class Type1Factory
{
private Type3 type3;
public Type1Factory(Type3 _type3)
{
type3 = _type3;
}
public GetType1(Type2 type2)
{
return new Type1(type2, type3);
}
}
这样称呼:
// SpellingChecker is subclass of Type3
IUnityContainer container = new UnityContainer();
container.RegisterType<Type3>(typeof(SpellingChecker));
// DocumentViewer is subclass of Type2
Type1Factory factory = container.Resolve<Type1Factory>();
Type1 type1 = factory.GetType1(new DocumentViewer());
这假设您只是尝试使用Unity来解析Type3依赖关系,并且您无法控制Type1中的构造函数。如果您可以编辑Type1,请使用Alexader R.的建议,使Unity仅解析一个参数构造函数。
答案 5 :(得分:0)
您可以使用容器层次结构,请在此处阅读我对类似问题的回答:Microsoft Unity. How to specify a certain parameter in constructor?。
唯一的区别是看起来应该在您的子容器中使用RegisterInstance()
而不是RegisterType()
。也许不是,这取决于您是否在代码之外的某个地方创建了实例。