代码之家  ›  专栏  ›  技术社区  ›  Nico Pizzo

子查询上的nhibernate联接

  •  0
  • Nico Pizzo  · 技术社区  · 6 年前

    我正在尝试对子查询与另一个表进行联接 我拥有以下实体:

    public class SomeClass
    {
        public virtual string KeyPart1 { get; set; }
        public virtual string KeyPart2 { get; set; }    
        public virtual int VersionNo { get; set; }
        public virtual string ClassProperty1 { get; set; }
        public virtual string ClassProperty2 { get; set; }
    }
    

    然后,我进行以下查询,以获取每条记录的最新版本:

    var subquery = QueryOver.Of<SomeClass>()
                      .SelectList(lst => lst
                                    .SelectGroup(f => f.KeyPart1)
                                    .SelectGroup(f => f.KeyPart2)
                                    .SelectMax(f => f.VersionNo));
    

    我现在正试图为子查询的每个结果返回整个SomeClass。 到目前为止,我有这样的想法:

    var query = QueryOver.Of<SomeClass>()
                     .WithSubquery.Where(???)
    

    SQL语句完成后应该是这样的

    SELECT cls.*
    FROM SomeClass as cls
    INNER JOIN
       (SELECT KeyPart1, KeyPart2, MAX(VersionNo)
        FROM SomeClass
        GROUP BY KeyPart1, KeyPart2) as sub
    ON sub.KeyPart1 = cls.KeyPart1 and sub.KeyPart2 = cls.KeyPart2 and sub.VersionNo = cls.VersionNo
    

    有人能帮我返回每个最高版本的整个SomeClass记录吗?

    编辑: 可以使用exist语句执行相同的操作吗?这将允许我们使用以下内容:

    SomeClass classAlias = null
    var subquery = QueryOver.Of<SomeClass>()
                      .SelectList(lst => lst
                                    .SelectGroup(f => f.KeyPart1)
                                    .SelectGroup(f => f.KeyPart2)
                                    .SelectMax(f => f.VersionNo))
                      .Where(x => x.KeyPart1 == classAlias.KeyPart1)
                      .Where(x => x.KeyPart2 == classAlias.KeyPart2)
                      .Where(x => x.VersionNo == classAlias.VersionNo)
    
    var query = Session.QueryOver(() => classAlias)
                   .WithSubQuery.WhereExists(subquery);
    

    生成以下SQL语句:

    SELECT *
    FROM SomeClass cls
    WHERE EXISTS
       (SELECT KeyPart1, KeyPart2, MAX(VersionNo)
        FROM SomeClass cls2
        WHERE cls.KeyPart1 = cls2.KeyPart1 and cls.KeyPart2 = cls2.KeyPart2 and cls.VersionNo = cls2.VersionNo
        GROUP BY KeyPart1, KeyPart2)
    

    然而,这也带来了所有版本,但我认为这将是另一个好的开始。

    1 回复  |  直到 6 年前
        1
  •  1
  •   Nico Pizzo    6 年前

    经过大量的尝试和错误,我能够在不存在的地方使用它。希望这能帮助有类似问题的人。

    以下是使用QueryOver返回特定记录最新版本的代码段:

    SomeClass classAlias = null
    var subquery = QueryOver.Of<SomeClass>()
                      .SelectList(lst => lst
                                    .SelectGroup(f => f.KeyPart1)
                                    .SelectGroup(f => f.KeyPart2)
                                    .SelectMax(f => f.VersionNo))
                      .Where(x => x.KeyPart1 == classAlias.KeyPart1)
                      .Where(x => x.KeyPart2 == classAlias.KeyPart2)
                      .Where(x => x.VersionNo > classAlias.VersionNo);
    
    var query = Session.QueryOver(() => classAlias)
                   .WithSubQuery.WhereNotExists(subquery);
    
    var results = query.List();