如何使用工厂设计模式创建复杂对象

问题描述 投票:0回答:1

您好,我必须创建一个复杂的对象,并且我想为其使用工厂模式。但是,我不知道如何处理对象才能创建的其他依赖项。

Dependencies

public class SomeService
{
}
public class SomeOtherService
{
}

Hierarchy

public abstract class NeededObjectBase
{
  public readonly int Type {get;set;}  //id selected by the factory

  public abstract void DoSomething();
}
public class A:NeededObjectBase
{
   private SomeService service;
   A(SomeService service){ this.service=service;}
   public override void DoSomething(){}
}
public class B:NeededObjectBase
{
   public B(SomeService service,SomeOtherService otherService){
       this.service=service;
       this.otherService=otherService
   }
   public SomeOtherService service;
   public SomeOtherService otherService;
   public override void DoSomething(){}
}

工厂

public class Factory
{
   public static NeededObjectBase CreateInstance(int type)
   {
       switch(type)
       {
        case 0:return new A();  //this would need SomeService => new A(someService)
        case 1:return new B();   // this would need SomeService & SomeOtherService => new B(someService,someOtherService);
        default: return new A();
       }
   }
}

用法

public class Aggregate
{
   private SomeService s1;
   private SomeOtherService s2;
   public void UseNeededObject(int type)
   {
     NeededObjectBase neededObject=Factory.CreateInstance(type);
     neededObject.DoSomething();
   }
}

如果查看代码,则将发生以下情况:我有一个Aggregate类,其中存放我的dependencies。在其方法内部,我使用基于Factory参数的type来创建正确的对象。但是我不知道如何处理依赖关系。工厂是否应该获得所有必需的依赖关系才能创建对象?

所以基本上我不知道谁应该保留对象创建的依赖关系。工厂进行选择,但是它如何提供正确的依赖关系以实例化选择?

P.S我需要以某种方式首先根据参数进行选择,并从工厂检索something,然后通过某种方式获取其依赖项以创建最终对象。

c# design-patterns dependencies factory
1个回答
1
投票

一种很好的方法是使用DI库,然后将其提供的任何容器注入工厂;然后,工厂仅根据传递的参数来决定应返回的类型,然后委托容器来构造该对象以进行返回。

这有一些好处

  • 它使您可以从工厂中分离这些依赖对象(实际上是构造对象)的生命周期
  • [它使工厂不必知道如何构造它提供的所有可能的对象图,并使它专注于对what进行构建,而不是how进行构建]

例如

public class SimpleFoo: Foo
{
    public  SimpleFoo(IServiceA a){...}
}

public class ComplexFoo: Foo
{
    public  ComplexFoo(IServiceA a, IServiceB b){...}
}

public class DegenerateFoo: Foo
{
    public DegenerateFoo(){..does nothing...}
}

public class FooFactory
{    
    readonly IContainer _container;
    public void FooFactory(IContainer container){_container=container;}

    public Foo GetAFoo(int type)
    {
       switch (type)
       {
            case 0:
                return _container.Get<SimpleFoo>();
            case 1:
                return _container.Get<ComplexFoo>();
            default:
                //unknown case, return some kind of Foo that does nothing
                return _container.get<DegenerateFoo>();
       }
    }
}

与此同时,您的容器将在应用程序的“合成根目录”中的其他位置进行单独配置,以了解如何解析对象图(以下仅为伪代码)

container.RegisterTransient<IServiceA, ServiceAImplementation>();
container.RegisterSingleton<IServiceB, ServiceBImplementation>();

在这种情况下,我们正在配置每次每次请求IServiceA注入都是一个新的对象实例;而IServiceB注入将是一个共享实例,容器将负责创建一次并根据请求分配。当然,这只是如何配置这些示例,最终您将最清楚地了解如何配置这些依赖项的生存期。

希望您有主意。

© www.soinside.com 2019 - 2024. All rights reserved.