代码之家  ›  专栏  ›  技术社区  ›  Afshar Mohebi

如何使用linq-to-nhibernate查询继承的类?

  •  2
  • Afshar Mohebi  · 技术社区  · 15 年前

    假设我有课 Animal , Cat Dog . 继承自 动物 . 考虑以下代码:

    var query = from animal in session.Linq<Animal>()
                where 
                animal.Color == "White"
                select animal;
    

    如何在上述查询中添加条件以查询实体类型?例如 animal.Type == typeof(Cat) .

    3 回复  |  直到 15 年前
        1
  •  1
  •   Community Mohan Dere    9 年前

    可以映射使用鉴别器列作为公式一部分的只读属性。查询此列将允许您区分具有当前nhcontrib提供程序的类型。

    在我对类似问题的回答中可以找到进一步的指导。 here .

        2
  •  11
  •   Diego Mijelshon    15 年前

    新提供程序支持此功能:

    var query = from animal in session.Query<Animal>()
                where animal.Color == "White" &&
                      animal is Cat
                select animal;
    
        3
  •  1
  •   James Kovacs    15 年前

    与nh 2.1.2兼容的linq-to-nhibernate版本不支持在运行时按类型查询。

    // DOES NOT WORK WITH NH 2.1.2 & LINQ-to-NH
    var desiredType = typeof(Cat);
    var query = from animal in session.Linq<Animal>()
                where animal.Color == "White"
                   && animal.GetType() == desiredType
                select animal;
    // This results in an ArgumentOutOfRangeException in the LINQ provider
    

    您可以按照注释中的建议在内存中执行此操作:

    var desiredType = typeof(Cat);
    var query = from animal in session.Linq<Animal>()
                where animal.Color == "White"
                select animal;
    var animals = query.ToList();
    var whiteCats = from animal in animals.AsQueryable()
                    where animal.GetType() == desiredType
                    select animal;
    

    通过执行query.tolist(),您将读取所有白色动物,然后使用linq to对象执行类型查询。(取决于您的确切查询和映射,您可能需要担心懒惰的代理,因此检查对象的类型是否可以分配给所需的类型。)这确实有一个主要的缺点,即为了在内存中按动物类型过滤,读取的数据比需要的要多。根据您的域和查询,这可能是一个大问题,也可能不是一个大问题。

    如果您不能升级到nhibernate主干(即nh3),我建议您不要为此查询使用linq to nhibernate,而是使用条件。

    var desiredType = typeof(Cat);
    var query = session.CreateCriteria(desiredType)
                       .Add(Restrictions.Eq("Color", "White")
                       .List<Animal>();
    

    注意,这应该是显而易见的,但让我明确地陈述一下。您没有理由不能使用此查询的条件以及Linq to nhibernate用于其他查询。您可以在nhibernate中自由混合匹配查询技术。