2

我有一个面向对象设计/数据库的问题。我正在使用实体框架 5 在 Microsoft MVC v4 中进行编码。假设模型如下:

public class Car
{
  public int Id {get; set;}
  public string Name {get; set; }
  public int Wheels {get; set;}
}
public class Truck : Car
{
  public int CargoCapacity {get; set;}
}
public class Bus : Car
{
  public int PassangerCapacity {get; set;}
}

在稍后阶段,我可能想要扩展模型,因此必须考虑这一点。例如:添加具有“NumberOfTurbos”属性的赛车。

遵循良好的 OO 设计原则:

问题 1: 这些都应该在单独的类中还是与修饰符合二为一。从面向对象的角度来看原则的分离,我会说将它们分开。此外,封闭/开放原则规定它们应该分开,这将有助于我稍后添加赛车,而不必改变任何关于公共汽车、卡车等的东西。

问题2: 它们应该都在同一个数据库表中吗?尽管我不认为类的数量应该决定表的数量,但我仍然会选择单独的表,以便对数据库进行规范化并且到处都没有未使用的字段。默认情况下,代码优先将所有内容放在一个表中,但我已将其与类模式属性分开。

问题 3: 如果我应该对接口而不是具体类进行编程(再次是 OO 原则),这将如何工作,因为如果我有像 ICar 这样由具体类 car 实现的东西,那么将东西转换为 ICar 将不起作用. 像 List < ICar > 这样的东西不会给我所有正确的数据。将 MVC 视图实现到接口 ICAR 也很困难。

我什至应该将接口放在仅属性类上吗?我应该在这里使用存储库或其他一些模式/想法吗?

为这个冗长的问题道歉,我很感激任何帮助。提前致谢。麦克风

4

3 回答 3

0

答案1:

是的,这些应该分成多个类。您可以通过标记Car为抽象来进一步扩展它,因为它是其他类型汽车的基类。您还必须将属性标记为抽象,如下所示:

abstract class Car
{
    abstract public int Id;
}

虽然这可能是一个更好的名字Vehicle

答案 2:

您可以将这些存储在一个表中,称为Vehicle并拥有一张VehicleType表。

桌车:

车辆名称车辆类型

1 丰田 1

2 川崎 2

表车辆类型:

Id VehicleDescription

1 辆车

2 摩托车

3 卡车

答案 3:

如果您使用了一个接口并且有一个列表,那么您将受限于该ICar接口公开的属性/字段。但是,您可以将其转换为适当的 VehicleType。

于 2013-10-02T22:17:25.653 回答
0

问题 1:这些都应该在单独的类中还是与修饰符合二为一。从面向对象的角度来看原则的分离,我会说将它们分开。封闭/开放原则也规定它们应该分开,这将有助于我稍后添加赛车,而不必改变任何关于公共汽车、卡车等的东西。

现实地分开类,每个项目类型一个类。这也将成为未来的证明,因为您对任何班级所做的任何更改都不一定会影响其他班级。任何添加的将来共享的东西都可以放在基类上。


问题2:它们应该都在同一个数据库表中吗?尽管我不认为类的数量应该决定表的数量,但我仍然会选择单独的表,以便对数据库进行规范化并且到处都没有未使用的字段。默认情况下,代码优先将所有内容放在一个表中,但我已将其与类模式属性分开。

不,绝对不是。是的,查询会更容易,但您查询的数据量实际上会增加。另外,您正在有效地对数据库设计进行非规范化,更不用说拥有大量可空字段,如果一种类型需要这些字段,而其他类型不需要这些字段,则可能会涉及一些丑陋的逻辑来验证。


问题 3:如果我应该对接口而不是具体类进行编程(再次是 OO 原则),这将如何工作,因为如果我有像 ICar 这样由具体类 car 实现的东西,那么将东西转换为 ICar 将不起作用. 像 List < ICar > 这样的东西不会给我所有正确的数据。将 MVC 视图实现到接口 ICAR 也很困难。

您不应该对接口进行编程,您应该选择完全依赖于实现的接口/基类。我会在您的示例中说,只需使用一个基类(VehicleBase您可以将所有共享属性放入其中。

于 2013-10-02T22:19:00.050 回答
0
  1. 是的,他们应该在不同的班级。模型中的实体不应具有逻辑上不“属于”它们的属性。在处理 aTruck时, set 或 read 很可能没有意义PassangerCapacity。那只会令人困惑。

  2. 这是在 ORM 层中做出的选择(在您的情况下为 EF)。EF 支持包含所有子类的属性列的单个表,以及子类的多个表。这两种选择都有其优点。单个表的连接较少,因此可能更快,但多个表减少了数据库必须存储、读取和写入的列数,因此在存储方面它可能更有效。这一切还取决于实际数据集的样子。然而,这将由 ORM 层 (EF) 抽象,因此在您的对象模型中它们仍然应该是分开的。

  3. 如果你的代码需要处理卡车,你应该让它处理卡车,对于只关心汽车的地方,使用 ICar。您的数据库层可以公开包含汽车、卡车和赛车的数据集。

于 2013-10-02T22:23:20.800 回答