如何使用nhibernate实现此设计。

时间:2014-10-23 13:19:31

标签: c# nhibernate

我有一个课程说Expense,受益人,可以是Desk或User,因此Expense有一个或多个受益人,它可以只有一种类型,所有Desk或所有具有不同重新分配的用户。

[DataContract]
[KnownType(typeof(User))]
[KnownType(typeof(Desk))]
public abstract class Beneficiare
{
    [DataMember]
    public virtual  int Id { get; set; }
    [DataMember]
    public virtual string FullName { get; set; }
}

[DataContract]
public class Desk : Beneficiare
{
    [DataMember]
    public virtual int NbEmployee { get; set; }
    //other properties and method
}

[DataContract]
public class User : Beneficiare
{
    [DataMember]
    public virtual string Surname { get; set; }
    [DataMember]
    public virtual string LastName { get; set; }
    //other properties and method
}

[DataContract]
public class ExpenseRepartition
{
    [DataMember]
    public virtual int Id { get; set; }
    [DataMember]
    public virtual Beneficiare Beneficiare { get; set; }
    [DataMember]
    public virtual Expense Expense { get; set; }
    [DataMember]
    public virtual Decimal Percentage { get; set; }
}

[DataContract(IsReference = true)]
public class Expense
{
    [DataMember]
    public virtual int Id { get; set; }
    [DataMember]
    public virtual DateTime COBDate { get; set; }
    [DataMember]
    public virtual Amount Amount { get; set; }
    [DataMember]
    public virtual IList<ExpenseRepartition> Repartition  { get; set; }
}

所以基本上,使用nhibernate,我可以用于桌面和用户a&#34;每个类层次结构的表&#34;或&#34;表格每个具体的子类&#34;。我不喜欢每班级使用表格,因为它们有很多不同的属性,因此我会在数据库中以一个包含大量列的表结束,其中很多都是空的。我不想从同一个对象继承用户和桌面,appart有一个完全不相关的名字。 相反,我想要做那样的事情

[DataContract]
public class Desk
{
    [DataMember]
    public virtual  int Id { get; set; }
    [DataMember]
    public virtual string Name { get; set; }
    [DataMember]
    public virtual int NbEmployee { get; set; }
    //other properties and method
}

[DataContract]
public class User
{
    [DataMember]
    public virtual  int Id { get; set; }
    [DataMember]
    public virtual string FullName { get; set; }
    [DataMember]
    public virtual string Surname { get; set; }
    [DataMember]
    public virtual string LastName { get; set; }
    //other properties and method
}

[DataContract]
[KnownType(typeof(ExpenseRepartitionUser))]
[KnownType(typeof(ExpenseRepartitionDesk))]
public abstract class ExpenseRepartition
{
    [DataMember]
    public virtual int Id { get; set; }
    [DataMember]
    public virtual Expense Expense { get; set; }
    [DataMember]
    public abstract string BeneficiareName { get; }
    [DataMember]
    public virtual Decimal Percentage { get; set; }
}


[DataContract]
public class ExpenseRepartitionDesk :ExpenseRepartition
{
    [DataMember]
    public virtual Desk Beneficiare { get; set; }

    public override string BeneficiareName
    {
        get
        {
            return Beneficiare.Name;
        }
    }

}

[DataContract]
public class ExpenseRepartitionUser : ExpenseRepartition
{
    [DataMember]
    public virtual User Beneficiare { get; set; }
    public override string BeneficiareName
    {
        get
        {
            return Beneficiare.FullName;
        }
    }

}

[DataContract(IsReference = true)]
public class Expense
{
    [DataMember]
    public virtual int Id { get; set; }
    [DataMember]
    public virtual DateTime COBDate { get; set; }
    [DataMember]
    public virtual Amount Amount { get; set; }
    [DataMember]
    public virtual IList<ExpenseRepartition> Repartition  { get; set; }
}

继承是在vastserepartition类而不是桌面和用户,知道百分比计算可能会有所不同,例如,如果用户根据用户填写它,如果它是&#39 ;对于桌子来说,这取决于桌子的员工人数/费用在重新分配中的员工总数。因此,在这种情况下,使用nhibernate a可以使用每个层次结构的表进行扩展重新分区,在一列中使用discriminator-value,或者在每个具体类中使用一个表,其中只有一列具有用户或桌面的id。什么是最佳解决方案/设计?或许还有另一个。

1 个答案:

答案 0 :(得分:0)

来自我们对nhibernate邮件列表的讨论

http://notherdev.blogspot.com/2012/01/mapping-by-code-inheritance.html

第三个选项是使用带有联合子类的每个子类的表。这次没有基类的单独表,在每个表中为子类分别指定公共列,子类表共享相同的密钥生成器。将union子类映射到代码映射非常简单 - 我们只需要通过继承UnionSubclassMapping映射该类 - 没有其他要求或选项。