2013-05-20 59 views
0

如果您有多个工厂实现,那么每个实例需要使用不同的状态信息来创建新对象时,会使用哪种模式?处理工厂实现中的状态

实施例: IModelParameters:包含所有的输入和输出到一个复杂的计算 IModelParameterFactory:具有用于获取和保存IModelParameter对象的方法。

问题是,一个工厂的实现可能是从数据库获取你的参数,需要一些检索所需的状态(例如UserID),另一个可能是从文件获取输入,在这种情况下你不需要有一个用户名,但你确实需要一个文件名。

在这种情况下是否有另一种模式更好?我看了一些依赖注入工具/库,并没有看到任何似乎解决这种情况的东西。

回答

0

你有没有试过把课程要求放在课堂上?

每个工厂实现都有其自己的requeriments,但所有的requeiments类派生形成一个基本的requeiment类(或阻碍一个requeriments接口)。这允许您为所有工厂实现具有相同的接口,您只需在每个工厂实现中对正确的requeriments类执行转换。

是的,转换是丑陋的和容易出错的,但是这种方法为工厂提供了一个统一的可扩展接口。

0

很难说没有看到一些代码,但你可能想要考虑实施一个存储库模式。 Repository实现将负责检索工厂用于构建其对象的数据。你可以注入仓库接口到你的工厂:

public class ModelParameterFactory : IModelParameterFactory 
{ 
    private readonly IModelParameterRepository Repository; 

    public ModelParameterFactory(IModelParameterRepository repository) 
    { 
     Repository = repository; 
    } 

    ...interface methods use the injected repository... 
} 

然后你会的,说DatabaseModelParameterRepository和FileModelParameterRepository。但我猜你也有周围那些你将需要注入的逻辑,这样要求另一家工厂:

public class ModelParameterRepositoryFactory : IModelParameterRepositoryFactory 
{ 
    public ModelParameterRepositoryFactory(...inputs needed to determine which repository to use...) 
    { 
     ...assign... 
    } 
    ...determine which repository is required and return it... 
} 

在这一点上,它可能会更有意义注入IModelParameterRepositoryFactory到ModelParameterFactory,而比注入IModelParameterRepository。

public class ModelParameterFactory : IModelParameterFactory 
{ 
    private readonly IModelParameterRepositoryFactory RepositoryFactory; 

    public ModelParameterFactory(IModelParameterRepositoryFactory repositoryFactory) 
    { 
     RepositoryFactory = repositoryFactory; 
    } 

    ...interface methods get repository from the factory... 
} 

无论您使用DI容器与否,对采用何种存储库,并利用其工厂现已搬进了相关工厂实现,而不是调用代码或DI配置的所有逻辑。

虽然不是非常复杂,但这种设计让我停下来想知道您的ModelParameterFactory和ModelParameters是否过于通用。你可以从嘲笑他们到单独的,更具体的课堂中受益。结果将是一个更简单,更具表现力的设计。但是,如果情况并非如此,以上应该适用于您。

0

以我的观点来看,状态是你存储在内存中的东西,比如静态对象,全局变量,缓存或会话。通常在DI中,这些状态不被维护,而是作为参数传递。示例:

public IEnumerable<Records> GetRecordByUserId(string userId){ /*code*/ } 

userId正在传递,而不是在存储库中维护。

但是,当你想让它们像配置一样,而不是每次你做查询时传递,我认为你可以注入它作为包装类。有关更多信息,请参阅我的question。但是,我不建议在存储库中使用这种设计,但我建议在服务级别。