如何避免在C#中基类的具体实现中进行强制转换?

时间:2019-09-09 04:49:56

标签: c# inheritance design-patterns interface

我正在编写一个概念证明数据库系统,其中我想定义数据库表和行的一些基本实现,然后从表示表和行的基类派生。因此,例如,我已经在我的项目中进行布局-

public interface ITable
{ 
    void InsertRow(BaseRow row); 
}

public abstract class BaseRow { }
public class ConcreteRowA : BaseRow {}
public class ConcreteRowB : BaseRow {}

public class ConcreteTableA : ITable
{
    public void InsertRow(BaseRow row)
    {
       if (row is ConcreteRowA)
       {
           var RowA = (ConcreteRowA)row;
       }
       // do stuff specific to a RowA type
    }
}

public class ConcreteTableB : ITable
{
    public void InsertRow(BaseRow row)
    {
       if (row is ConcreteRowB)
       {
           var RowB = (ConcreteRowB)row;
       }
       // do stuff specific to a RowB type
    }
}

我试图避免在实现中对类型进行检查和转换,因此,如果--

public class ConcreteTableA : ITable
{
    public void InsertRow(ConcreteRowA row)
    {
       // do stuff specific to a RowA type
    }
}

public class ConcreteTableB : ITable
{
    public void InsertRow(ConcreteRowB row)
    {
       // do stuff specific to a RowB type
    }
}

但是我知道,当我实现一个接口时,这种方式是行不通的。是正确的,还是我误解了如何使用抽象类和接口?有没有更好的方法来实现我要执行的操作?

从本质上讲,我想对类ConcreteTableA和ConcreteTableB强制使用相同类型的方法“ InsertRow”,但是接受特定于其实现的类型的参数(ConcreteRowA或ConcreteRowB)。我的设计有缺陷吗?我觉得我必须违反一些原则。

1 个答案:

答案 0 :(得分:1)

您要声明使用特定类型的行的表的具体实例。这是generics的很好的候选人。您可以将接口声明修改为enforce a constraint所需的行类型;

public interface ITable<TRow> where TRow : IRow
{ 
    void InsertRow(TRow row); 
}

然后您可以定义;

public class ConcreteTableA : ITable<ConcreteRowA>
{
    void InsertRow(ConcreteRowA row); 
}

public class ConcreteRowA : IRow
{

}

public class ConcreteTableB : ITable<ConcreteRowB>
{
    void InsertRow(ConcreteRowB row); 
}

public class ConcreteRowB : IRow
{

}