在保留一些扩展能力的同时统一两个类。简单性与可重用性

时间:2012-07-13 14:52:20

标签: design-patterns code-reuse

注意:我的代码恰好是在C#中,但我不认为这对解决问题很重要。

问题

我正在尝试减少我们拥有的两个旧类中的代码重复,这两个类都用于从XML加载查询。它们都具有采用XML位置的构造函数,两者都具有接受SQL参数集合的Execute方法,并且都提供各种静态重载方法,以便使用单个命名参数快速轻松地运行查询,或者没有参数,或者具有非默认SQL连接对象的参数。这些静态方法也接受XML位置作为参数,并在内部调用构造函数,依此类推,最后只返回DataSet的第一个DataTable。

public static DataTable GetQuery(string queryName) { ... }
public static DataTable GetQuery(string queryName, string parameterName, string parameterValue) { ... }
public static DataTable GetQuery(string queryName, Hashtable parameters) { ... }
public static DataTable GetQuery(string queryName, Hashtable parameters, IConnection connection) { ... }

等等。

两者之间的差异是在文件系统中查找XML文件,另一个在程序集中查找它们。

可能的解决方案1 ​​

我正在考虑将它们统一为一个可以执行任何操作,使用单独的IQuerySource接口的不同实现,传递给构造函数或其他内容。但这意味着要么必须提前调用构造函数,要么每次都需要将GetQuery方法传递给IQuerySource对象。我试图避免这样的事情,因为这些GetQuery方法在客户端代码中用于无处不在,用于快速的小事情,例如GetQuery("GetUserDetails","UserID",userId.ToString())

可能的解决方案2

或者,我可以创建两个非常轻松的类FileQueryDllQuery,它们将位于统一类的顶部,它们将始终通过FileQuerySource和{{1}向下到构造函数和/或DllQuerySource方法。这会使客户端代码变小,但除了核心类之外,我不希望在另外两个地方维护(略微更薄)所有现有GetQuery重载的版本!

可能的解决方案3

另一个替代方案就像上面这样,但是暴露统一类,所以你可以调用,比如GetQuery,但是后来我不确定DllQuery如何拦截调用并确保Q的实例统一班级总能找到合适的工作来源。

另一个复杂性是,从程序集中获取XML,我们当前正在使用DllQuery.Q.GetQuery("GetUserDetails","UserID",userId.ToString()),因此无论何处调用必须直接位于客户端代码的表面下,否则我们将获得数据程序集而不是客户端程序集。

我理解这个问题可能有点主观,但我希望有一些易于理解和明确定义的设计模式或其他东西来解决这个问题。

1 个答案:

答案 0 :(得分:2)

我认为这很受意见的影响,但我这样做:

public interface IQuerySource
{
  // function GetXML(Assembly caller)
};

public class XmlQuery
{
  XmlQuery(IQuerySource source);
  // GetQuery functions
}

public class FileQuery : IQuerySource
{
  private FileQuery() {} // Only accessable through the Q property
  public static readonly XmlQuery Q = new XmlQuery(new FileQuery());

  // function GetXML(Assembly caller) for a file source
}

public class DllQuery : IQuerySource
{
  private DllQuery() {} // Only accessable through the Q property
  public static readonly XmlQuery Q = new XmlQuery(new DllQuery());

  // function GetXML(Assembly caller) for an assembly source
}