1

我有一个界面:

public interface IHHSDBUtils
{
    void SetupDB();

    bool TableExists(string tableName);
    . . .

...有多个实施者:

public class SQLiteHHSDBUtils : IHHSDBUtils
public class SQCEHHSDBUtils : IHHSDBUtils
public class FlatfileHHSDBUtils : IHHSDBUtils
public class TestHHSDBUtils : IHHSDBUtils

我希望能够从全局可访问的位置指定将使用哪个实施者,例如:

public static class HHSConsts
{
    public static IHHSDBUtils hhsdbutil = SQLiteHHSDBUtils;

...然后从应用程序的任何位置这样调用它:

private HHSDBUtils hhsdbutils { get; set; }
. . .
hhsdbutils = new HHSConsts.hhsdbutil;
hhsdbutils.SetupDB();

这可能吗?我明白了,“'SQLiteHHSDBUtils' 是一个'类型',但它像一个'变量'一样使用,它分配给上面的 hhsdbutil。

4

1 回答 1

2

您可以通过为每种类型创建一个枚举并拥有一个为您创建该类型的静态工厂方法来执行穷人工厂实现。我尽可能靠近您当前的代码片段。

public enum HHSDBUtilsTypes 
{
    Sqllite,
    SQCE,
    Flatfile,
    Test
}

public static class HHSConsts
{
    private const string implementation = HHSDBUtilsTypes.Sqllite; // you might read this from the config file

    public static IHHSDBUtils GetUtils()
    {
         IHHSDBUtils impl;
         switch(implementation)
         {
            case HHSDBUtilsTypes.Sqllite:
               impl = new SQLiteHHSDBUtils();
            break;
            case HHSDBUtilsTypes.SQCE:
               impl = new SQCEHHSDBUtils();
            break;
            case HHSDBUtilsTypes.Sqllite:
               impl = new FlatfileHHSDBUtils();
            break;
            default:
               impl = new TestHHSDBUtils();
            break;
         }
         return impl;
    }
}

你会像这样使用它:

private IHHSDBUtils hhsdbutils { get; set; }
//. . .
hhsdbutils = HHSConsts.GetUtils();
hhsdbutils.SetupDB();

另一种选择是使用Activator.CreateInstance

 const string fulltypename = "Your.Namespace.SQLiteHHSDBUtils"; // or read from config;
 hhsdbutils = (HHSDBUtils) Activator.CreateInstance(null, fulltypename).Unwrap();

确保测试和测量性能,特别是如果您需要经常通过这些方法中的任何一种来实例化很多类型。

如果您想要更多控制,请使用依赖注入/控制反转框架,例如:

请注意,尽管所有这些框架都带来了自己强大的功能,但也增加了复杂性。如果您觉得必须选择一个框架,请将可维护性和可学习性作为主要要求。

这是关于 DI的一些额外文档

于 2014-12-01T21:20:55.150 回答