2

所以这对我来说似乎有点复杂,所以我会尝试首先尽可能清晰地设置场景。

[ActiveRecord, JoinedBase]
abstract BaseClass
{
    public x;
    public y;
}

[ActiveRecord, JoinedBase]
ClassA : BaseClass { }

[ActiveRecord, JoinedBase]
ClassB : BaseClass { }

abstract GraphicBaseClass : BaseClass
{
    public height;
    public width;
}

[ActiveRecord, JoinedBase]
ClassC : GraphicBaseClass { }

[ActiveRecord, JoinedBase]
ClassD : GraphicBaseClass { }

[ActiveRecord, JoinedBase]
ClassE : GraphicBaseClass { }

注意:为了保存在我需要输入的文字墙上,忽略了几个关键字和其他绒毛。

所以文字解释...我们有一个标准的基类“BaseClass”,它实现了许多属性。然后我们有几个类“ClassA”和“ClassB”,它们是基础的特定类型。然后,我们使用一个中间基类“GraphicBaseClass”,它添加了高度和宽度属性,其余 3 个类继承自这些属性。这会产生单个 BaseClass 公用表,以及每个具体类的 5 个特定表。

我有一个查询,大多数情况下都适用于基本属性。在某些情况下,我想查询高度和宽度。由于 GraphicBaseClass 不是一个 activerecord 类,我不能将其用作查询的基础。目前我正在使用 QueryOver 语法,但我找不到一种方法来查询具有高度和宽度属性的三个 GraphicBaseClass 派生实体。

到目前为止,我得到的最接近的是:

QueryOver<BaseClass, BaseClass> query = QueryOver.Of<BaseClass>()
    .Where(bc => bc.x == something)
    .TransformUsing(CriteriaSpecification.DistinctRootEntity);
if (actualTypes.All(x => x.IsSubclassOf(typeof (GraphicBaseClass))))
{
    // Filter by dimensions
    if (criteria.RestrictSize)
    {
        if (criteria.FilterByDimension)
        {
            query.DetachedCriteria.Add(Restrictions.Lt("Width", criteria.Width + 10));
            query.DetachedCriteria.Add(Restrictions.Lt("Height", criteria.Height + 10));
        }
    }
}

这导致 sql 类似于:

SELECT TOP (4 /* @p0 */) this_.BaseClassId as BaseClass1_97_5_,
                 this_.Version                   as Version97_5_,
                 this_.BaseClassType          as BaseClass2_97_5_,
                 this_1_.Width                   as Width99_5_,
                 this_1_.Height                  as Height99_5_,
                 this_2_.Width                   as Width100_5_,
                 this_2_.Height                  as Height100_5_,
                 this_3_.X                       as X101_5_,
                 this_4_.Width                   as Width102_5_,
                 this_4_.Height                  as Height102_5_,
                 this_5_.X                       as X103_5_,
FROM   BaseClass this_
       left outer join ClassC this_1_
         on this_.BaseClassId = this_1_.ClassCId
       left outer join ClassD this_2_
         on this_.BaseClassId = this_2_.ClassDId
       left outer join ClassA this_3_
         on this_.BaseClassId = this_3_.ClassAId
       left outer join ClassE this_4_
         on this_.BaseClassId = this_4_.ClassEId
       left outer join ClassB this_5_
         on this_.BaseClassId = this_5_.ClassBId
WHERE  and this_1_.Width between 0 /* @p8 */ and 'Height' /* @p9 */

因此,它仅将高度和宽度限制应用于 3 个必需类之一。

我在这里寻找任何答案,如果它可以在 HQL 或 Criteria API 或实现结果所需的任何东西中完成。

为文字墙道歉!

谢谢。

4

1 回答 1

3

有点晚了,我知道。这是我通常使用的解决方案:

创建一个子查询并用“in”加入它。

if (/* subclass required*/)
{
  var subClassQuery = QueryOver.Of<GraphicBaseClass>();
  subClassQuery.Where(x => x.Width  == criteria.Width);
  subClassQuery.Where(x => x.Height == criteria.Height);
  subClassQuery.Select(x => x.Id);
  query.Where(Subquery.WherePropery(x => x.Id).In(subClassQuery));
}
于 2016-06-13T15:54:16.867 回答