每个层次结构组的实体框架4.2表由鉴别器组成

时间:2011-12-07 22:31:07

标签: vb.net group-by ef-code-first table-per-hierarchy discriminator

我正在使用EF 4.2代码优先模型开发项目。此模型包含产品的TPH继承结构。我需要在鉴别器上对这个继承模型的多态结果进行分组,并遇到一些问题。

实体框架不会公开鉴别器来完成此分组。我的第一个问题是我可以直接访问这个鉴别器吗?我的阅读和经验告诉我没有,所以我提出了这种解决方案。它表现不佳,我对如何维护它感到不满。

我的课程看起来像这样(简化):

Public MustInherit Class Product
      <key()>  
      Public Property ProductID as integer

      <StringLength(50, ErrorMessage:="Max 50 characters")>
      <Required(ErrorMessage:="Product name is required")>
      Public Property Name as String

      <TimeStamp()>
      Public Property Time_Stamp as DateTime = DateTime.Now()
End Class

Public Class Desktop
      Inherits Product

      <StringLength(50, ErrorMessage:="Max 50 characters")>
      <Required(ErrorMessage:="Processor is required")>
      Public Property Processor as String
End Class

Public Class Monitor
      Inherits Product

      <Required(ErrorMessage:="Monitor size is required")>
      Public Property Size_Inches as Integer
End Class

我构建了一个扩展方法,它接受一个产品并将其基类型名称作为字符串返回。

<Extension()>
Public Function ProductType(ByVal inProduct as Product) as String
      ProductType = inProduct.GetType().BaseType.Name
End Function

有了这个,我构建了这个结构来按类型对产品的结果进行分组,以便我可以运行它们:

Dim tmpProducts = db.Products.ToList()
Dim GrpProducts = tmpProducts.GroupBy(Function(prod) prod.ProductType) _
                             .Select(Function(s) New With {.ProductType = S.Key,
                                                           .Products = S })

我现在可以遍历列表以获得我想要的行为,但性能并不理想,我担心随着产品数量的增长,这将是不可接受的。

For Each ProductGroup in GrpProducts
       Dim TypeName as String = ProductGroup.ProductType
       Dim TypeProducts = ProductGroup.Products
Next

此外,这可以让我轻松访问共享属性(Name),但现在我没有很多选项可以将它们转换为真实类型,也许是TypeName的选择案例。 。

任何建议都表示赞赏,也请原谅上面的任何代码错误,我从内存中重新输入了示例,因为我目前无法访问该项目。

2 个答案:

答案 0 :(得分:2)

解决方案是更多地建模,并且拥有一个具有属性ProductType的新实体Name。然后,您会在ProductProductType之间建立一个简单的1-N关系。我没有使用EntityFramework,但是使用NHibernate,您可以轻松地让框架始终在查询中加入该表,这样就不会为每个ProductType返回Product的代理},这可能会损害表现。

作为附加组件,将来ProductType可以开发其他有趣的属性(例如Product的每个ProductType常见的值,因此它增加了灵活性您的解决方案,尽管它确实会立即为您的数据库添加另一个表。

答案 1 :(得分:1)

遵循Linq查询应该为您提供一种通过鉴别器

来解决分组的方法
from a in db.Records
group a.ID by new
{
    Name= a is Audio ? "Audio" :
            a is Video ? "Video" :
            a is Picture ? "Picture" :
            a is Document ? "Document" : "File"
} into g
select new 
{
    Name = g.Key.Name,
    Total = g.Count()
}