c# - 建模(和映射)具有两个多态性的类层次结构?

标签 c# oop nhibernate mapping polymorphism

我遇到了这样一种情况,在父/子层次结构中,我有两层多态性,一层在另一层中。

我认为最好用一个简单的例子来解释:

    class Group
    {
        public IList<Person> People { get; set; }
    }

    class SpecialGroup : Group
    {
        public IList<SpecialPerson> People { get; set; }
    }

    class Person {}

    class SpecialPerson : Person {}

所以一个Group有一个Person对象的列表,而一个专门的Group(SpecialGroup)有一个专门的Person(SpecialPerson)对象的列表。

这可以编译,但我收到一条警告,说我应该在 SpecialGroup.People 上使用“new”关键字,因为它隐藏了 Group.People 属性。

我理解这意味着什么,但也许我不完全理解您如何在 C# 中正确地建模这样的东西。关于如何以更好的方式对此建模有任何想法吗?

此外,知道这将如何与 NHibernate 一起使用吗?我不确定使用“new”关键字是否会减少它,因为 Group.People 属性已经映射到不同的类型。有没有更好的方法来建模,以与 NH 兼容的方式?


好吧,我想到了一种使用泛型对其进行建模的方法:

    abstract class AbstractGroup<PersonType>
        where PersonType : Person
    {
        public IList<PersonType> People { get; set; }
    }

    class Group : AbstractGroup<Person>
    {}

    class SpecialGroup : AbstractGroup<SpecialPerson>
    {}

    class Person {}

    class SpecialPerson : Person {}

我认为这符合我的要求?现在 Person 可以与 SpecialPerson 共享特征,但只能将 SpecialPerson 添加到 SpecialGroup。 AbstractGroup 基本类型可以对任何组的共同特征进行建模。

现在的问题是,如果我尝试映射它,NH 会爆炸吗?


郑重声明,似乎有些人已经成功地使用泛型类的查询 - 对于 HQL 查询(我的用例),这是不受支持的。

我想到的另一种方法是简单地隐藏父属性的实现,例如对子类中的覆盖属性使用“new”关键字 - 以下线程讨论了为什么它也不起作用:

NHibernate: Table Per Subclass Mapping and the New Keyword

到目前为止的结论:运行时检查和异常,正如下面@empi 所建议的。

最佳答案

这种情况也称为“平行”或“双重”继承。

通常在一个层次结构中有一个特定的类,它与另一个层次结构相关。

虽然不是必需的,但每个类都有一个“通用”或“抽象”类更好,它必须被覆盖,但是,已经有了依赖的概念。

这种情况在图形界面控件中非常有用,但是, 可能适用于其他场景。

在这种特殊情况下,通常只显示第一级会更好:

............................................................
....+----------------+................+----------------+....
....|  <<Abstract>>  |..<<contains>>..|  <<Abstract>>  |....
....| AbstractGroup  +<>--------------+ AbstractPerson |....
....|                |................|                |....
....+----------------+................+----------------+....
............................................................

尽管如此,您可以对多个级别进行建模,但不推荐:

............................................................
....+----------------+................+----------------+....
....|  <<Abstract>>  |..<<contains>>..|  <<Abstract>>  |....
....| AbstractGroup  +<>--------------+ AbstractPerson |....
....|                |................|                |....
....+-------+--------+................+--------+-------+....
............|..................................|............
............|..................................|............
............^..................................^............
............|..................................|............
............|..................................|............
....+-------+--------+................+--------+-------+....
....|  <<Concrete>>  |..<<contains>>..|  <<Concrete>>  |....
....|      Group     +<>--------------+     Person     |....
....|                |................|                |....
....+----------------+................+----------------+....
............|..................................|............
............|..................................|............
............^..................................^............
............|..................................|............
............|..................................|............
....+-------+--------+................+--------+-------+....
....|  <<Concrete>>  |..<<contains>>..|  <<Concrete>>  |....
....|   SchoolGroup  +<>--------------+     Student    |....
....|                |................|                |....
....+----------------+................+----------------+....
............................................................

您提到 NHibernate,您的类是否表示要存储的数据?

一些类似的问题:

Avoiding parallel inheritance hierarchies

Parallel Inheritance Hierarchy Refactoring

How to avoid parallel inheritance hierarchies among GUI controls and domain objects

Parallel Inheritance between Interface Classes and Implementation Classes in C++

干杯。

关于c# - 建模(和映射)具有两个多态性的类层次结构?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9436605/

相关文章:

c# - 如何检测 C# 类中的方法是否实现了接口(interface)中的方法?

c# - 如何使用 VSTO 2005 SE 通过 C# Excel 加载项创建 Excel 2003 UDF

oop - 内部类(class)的目的?

Python 多态性

java - 多对多关系的面向对象方法

c# - NHibernate 标准 : Add a constraint for property type

NHibernate Cascade none 仍在更新相关实体

c# - 如何在 C# 中对整数的特定字节执行 -1?

c# - 比较时,没有关键字段的 VB.NET 匿名类型与 C# 匿名类型有何不同?

c# - 如何模拟/ stub Nhibernate QueryOver 调用?