2009-11-10 86 views
0

我在嘗試將以下HQL查詢轉換爲條件。將HQL查詢轉換爲條件會生成無效的SQL

from SubportfolioAudit as a 
where a.ID in (select max(a2.ID) 
       from SubportfolioAudit as a2 
       where a2.EffectiveDate = :EffectiveDate 
        and a.Subportfolio.ID = a2.Subportfolio.ID 
       group by a2.Subportfolio.ID) 
and a.Subportfolio.ID in (:SubportfolioList) 

到目前爲止,我有以下幾點:

var crit = Session.CreateCriteria(typeof(SubportfolioAudit)); 
var currentAuditByEffectiveDate = DetachedCriteria.For(typeof(SubportfolioAudit)) 
            .SetProjection(Projections.ProjectionList() 
                .Add(Projections.Max("ID")) 
                .Add(Projections.GroupProperty("Subportfolio.ID"))) 
            .Add(Expression.Eq("EffectiveDate", effectiveDate)); 

crit.Add(Subqueries.PropertyIn("ID", currentAuditByEffectiveDate)); 
crit.Add(Expression.In("Subportfolio.ID", subportfolioList.Select(x => x.ID).ToArray())); 

return crit.List<SubportfolioAudit>(); 

產生無效的子查詢,你可以在這裏看到:

SELECT this_.SubportfolioAuditId  as Subportf1_21_6_, 
     this_.Event      as Event21_6_, 
     this_.CreatedDate    as CreatedD3_21_6_, 
     this_.[User]      as User4_21_6_, 
     this_.EffectiveDate    as Effectiv5_21_6_, 
     this_.SubportfolioId    as Subportf6_21_6_, 
     subportfol2_.SubportfolioId  as Subportf1_12_0_, 
     subportfol2_.PACERCode   as PACERCode12_0_, 
     subportfol2_.HedgeRatio   as HedgeRatio12_0_, 
     subportfol2_.Name    as Name12_0_, 
     subportfol2_.Strategy   as Strategy12_0_, 
     subportfol2_.BasketId   as BasketId12_0_, 
     subportfol2_.PortfolioId   as Portfoli7_12_0_, 
     subportfol2_.ReferenceBasketId as Referenc8_12_0_, 
     (SELECT CASE 
       WHEN Count(*) > 0 
       THEN 1 
       ELSE 0 
       END 
     FROM Asset 
     WHERE Asset.SubportfolioId = subportfol2_.SubportfolioId) as formula1_0_, 
     basket3_.BasketId    as BasketId7_1_, 
     basket3_.Name     as Name7_1_, 
     basket3_.CatsBenchmarkCode  as CatsBenc4_7_1_, 
     basket3_.Description    as Descript5_7_1_, 
     basket3_.BaseBasketId   as BaseBask6_7_1_, 
     basket3_.Filename    as Filename7_1_, 
     basket3_.Type     as Type7_1_, 
     basket4_.BasketId    as BasketId7_2_, 
     basket4_.Name     as Name7_2_, 
     basket4_.CatsBenchmarkCode  as CatsBenc4_7_2_, 
     basket4_.Description    as Descript5_7_2_, 
     basket4_.BaseBasketId   as BaseBask6_7_2_, 
     basket4_.Filename    as Filename7_2_, 
     basket4_.Type     as Type7_2_, 
     portfolio5_.PortfolioId   as Portfoli1_5_3_, 
     portfolio5_.BaseCurrencyCode  as BaseCurr2_5_3_, 
     portfolio5_.TradingAccountNumber as TradingA3_5_3_, 
     portfolio5_.Name     as Name5_3_, 
     portfolio5_.ClientId    as ClientId5_3_, 
     client6_.ClientId    as ClientId4_4_, 
     client6_.ExplicitFee    as Explicit2_4_4_, 
     client6_.Affiliated    as Affiliated4_4_, 
     client6_.ClientGroup    as ClientGr4_4_4_, 
     client6_.RCODA     as RCODA4_4_, 
     client6_.Name     as Name4_4_, 
     client6_.BaseCurrencyCode  as BaseCurr7_4_4_, 
     client6_.Region     as Region4_4_, 
     basket7_.BasketId    as BasketId7_5_, 
     basket7_.Name     as Name7_5_, 
     basket7_.CatsBenchmarkCode  as CatsBenc4_7_5_, 
     basket7_.Description    as Descript5_7_5_, 
     basket7_.BaseBasketId   as BaseBask6_7_5_, 
     basket7_.Filename    as Filename7_5_, 
     basket7_.Type     as Type7_5_ 
FROM dbo.SubportfolioAudit this_ 
     inner join dbo.Subportfolio subportfol2_ 
     on this_.SubportfolioId = subportfol2_.SubportfolioId 
     left outer join dbo.Basket basket3_ 
     on subportfol2_.BasketId = basket3_.BasketId 
     left outer join dbo.Basket basket4_ 
     on basket3_.BaseBasketId = basket4_.BasketId 
     left outer join dbo.Portfolio portfolio5_ 
     on subportfol2_.PortfolioId = portfolio5_.PortfolioId 
     left outer join dbo.Client client6_ 
     on portfolio5_.ClientId = client6_.ClientId 
     left outer join dbo.Basket basket7_ 
     on subportfol2_.ReferenceBasketId = basket7_.BasketId 
WHERE this_.SubportfolioAuditId in (SELECT max(this_0_.SubportfolioAuditId) as y0_, 
               this_0_.SubportfolioId   as y1_ 
            FROM  dbo.SubportfolioAudit this_0_ 
            WHERE this_0_.EffectiveDate = '2009-09-11T00:00:00.00' /* @p0 */ 
            GROUP BY this_0_.SubportfolioId) 
     and this_.SubportfolioId in (13 /* @p1 */,14 /* @p2 */,15 /* @p3 */,16 /* @p4 */, 
            17 /* @p5 */,18 /* @p6 */,19 /* @p7 */,20 /* @p8 */, 
            21 /* @p9 */) 

我知道Projections.GroupProperty()造成這個問題,但我似乎無法找到另一種方式來實現我想要的。

+0

但爲什麼你要設置Projections.Max(「ID」)? – Sly 2009-11-10 08:09:03

回答

1

我相信(並糾正我,如果我錯了),子查詢是無效的,因爲你缺少你在HQL中設置的第二個where子句(...和a.Subportfolio.ID = a2.Subportfolio。 ID)。

轉換您的標準查詢如下我相信(無法驗證,因爲我無法測試您的代碼),它會做的伎倆。

var crit = Session.CreateCriteria(typeof(SubportfolioAudit), "mainQuery"); 
var currentAuditByEffectiveDate = DetachedCriteria.For(typeof(SubportfolioAudit),"subQuery") 
       .SetProjection(Projections.ProjectionList() 
           .Add(Projections.Max("ID")) 
           .Add(Projections.GroupProperty("Subportfolio.ID"))) 
       .Add(Expression.Eq("EffectiveDate", effectiveDate)); 
       .Add(Expression.EqProperty("subQuery.ID", "mainQuery.ID")); 

crit.Add(Subqueries.PropertyIn("mainQuery.ID", currentAuditByEffectiveDate)); 
crit.Add(Expression.In("mainQuery.Subportfolio.ID", subportfolioList.Select(x => x.ID).ToArray())); 

return crit.List<SubportfolioAudit>(); 

我所做的是增加一個額外的,其中在的DetachedCriteria子句「連接」與外主查詢子查詢的SubportfoliAudit.ID列。我還提供了別名來命名查詢。

+0

謝謝,當我進入辦公室時給它一個鏡頭。 – NotMyself 2009-11-10 14:28:07

+0

是的,你的代碼產生同樣的問題。基本上,子查詢返回在IN語句中使用的兩列無效。 – NotMyself 2009-11-10 15:59:48

+0

得到它必須完全放棄組屬性它反正不需要。謝謝! – NotMyself 2009-11-10 16:18:18