gpt4 book ai didi

c# - 使用 StructureMap 注入(inject)相应的实现

转载 作者:太空宇宙 更新时间:2023-11-03 11:00:00 26 4
gpt4 key购买 nike

我有一个具有以下结构的类

class Measure
{
public MeasureType measureType { get; set; }
public readonly IMeasureService _service ;

public Measure(IMeasureService service)
{
_service = service;
}
public Calculate()
{
_service.Calculate(this);
}
}

所以我对不同的 measureTypes 有不同的 MeasureService 实现。是否可以使用StructureMap根据measureType注入(inject)对应的MeasureService。

MeasureType 只是一个枚举类型,在整个实例中永远不会改变。

最佳答案

由于一个简单的原因,不能指示 StructureMap 这样做:

  • 在创建实例时,无法设置 measureType 属性。
  • 您以后不能设置IMasureService 依赖项,因为它是只读(并且可能也应该是private)

因此,与 StructureMap 相比,此问题的解决方案更多地与类的设计有关。

在这种情况下,我通常会选择以下解决方案:


1) 将选择正确的 IMeasureService 实现的任务委托(delegate)给不同的组件。

例如,该组件可以称为 MeasureServiceFactory 并具有以下实现:

public class MeasureServiceFactory
{
private readonly Func<MeasureServiceType1> _type1Service;
private readonly Func<MeasureServiceType2> _type2Service;

public MeasureServiceFactory(
Func<MeasureServiceType1> type1Service,
Func<MeasureServiceType2> type2Service)
{
_type1Service = type1Service;
_type2Service = type2Service;
}

public IMeasureService GetServiceForType(MeasureType type)
{
switch (type)
{
case MeasureType.Type1:
return _type1Service();
case MeasureType.Type2:
return _type2Service();
default:
throw new ApplicationException("Unexpected measure type!");
}
}
}

请注意,StructureMap 会通过适当调用容器的 GetInstance() 方法自动注入(inject)两个 Func,以便正确解析所需的服务。

现在,Measure 类将不再直接依赖于 IMeasureService,而是依赖于工厂:

public class Measure
{
public MeasureType measureType { get; set; }
private readonly MeasureServiceFactory _measureServiceFactory;

public Measure(MeasureServiceFactory measureServiceFactory)
{
_measureServiceFactory = measureServiceFactory;
}

public void Calculate()
{
var service = _measureServiceFactory.GetServiceForType(measureType);
service.Calculate(this);
}
}

请注意,不需要配置 StructureMap。容器将能够正确解决所有问题。


2) 为了保持Measure 类不变,您可以让MeasureServiceFactory 实现IMeasureService 接口(interface):

public class MeasureServiceFactory : IMeasureService
{
private readonly Func<MeasureServiceType1> _type1Service;
private readonly Func<MeasureServiceType2> _type2Service;

public MeasureServiceFactory(
Func<MeasureServiceType1> type1Service,
Func<MeasureServiceType2> type2Service)
{
_type1Service = type1Service;
_type2Service = type2Service;
}

public void Calculate(Measure measure)
{
var service = GetServiceForType(measure.measureType);

service.Calculate(measure);
}

private IMeasureService GetServiceForType(MeasureType type)
{
switch (type)
{
case MeasureType.Type1:
return _type1Service();
case MeasureType.Type2:
return _type2Service();
default:
throw new ApplicationException("Unexpected measure type!");
}
}
}

现在,使用您的原始 Measure 类,只需这个 SM 配置即可使一切正常:

x.For<IMeasureService>().Use<MeasureServiceFactory>();

3) 如果IMeasureService implementors 内部的逻辑不是很复杂,可以考虑把它放在一个单独的类中,根据measureType 执行不同的事情>Measure 对象(您已经可以访问该对象)。

我知道,这似乎是退步,但在某些情况下我更愿意这样做:当业务逻辑不太复杂且不太可能改变时。

关于c# - 使用 StructureMap 注入(inject)相应的实现,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18063267/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com