亚音速查询条件A AND((条件B和条件C)OR(条件D和条件E和条件F)

时间:2012-02-02 19:24:32

标签: c# asp.net sql-server subsonic subsonic2.2

我接近拔出剩下的头发,因为我无法弄清楚如何在SubSonic 2.2中执行以下T-SQL查询:

SELECT  SalesRep, Location, InvoiceNumber, PONumber, POReceivedOn, SurgeryDate, Surgeon
FROM    dbo.vSalesRepCommissionGrouped AS vsrcg
WHERE   UserID IN ( 5, 6, 20 )
    AND ( ( SurgeryDate >= '2012-01-01'
            AND SurgeryDate <= '2012-01-31'
          )
          OR ( SurgeryDate >= '2011-12-01'
               AND SurgeryDate <= '2011-12-31'
               AND POReceivedOn >= '2012-01-01'
             )
        )
ORDER BY SurgeryDate ASC

我已经尝试过以下至少10种不同的方式使用以下SubSonic Select,但我无法让它产生相同的结果。

new Select("SalesRep, Location, InvoiceNumber, PONumber, POReceivedOn, SurgeryDate, Surgeon")
                    .From(VSalesRepCommissionGrouped.Schema)
                    .WhereExpression("UserID").In(new[] { 5, 6, 20 })
                    .AndExpression("SurgeryDate").IsGreaterThanOrEqualTo(BeginDate).And("SurgeryDate").IsLessThanOrEqualTo(EndDate)
                    .Or("SurgeryDate").IsGreaterThanOrEqualTo(BeginDate.AddMonths(-1)).And("SurgeryDate").IsLessThanOrEqualTo(
                        EndDate.AddMonths(-1)).And("POReceivedOn").IsGreaterThanOrEqualTo(BeginDate).CloseExpression()
                    .OrderAsc("SurgeryDate");

有人可以指出我正确的方向吗?

谢谢!   - 安德鲁

3 个答案:

答案 0 :(得分:1)

实际上,你的SubSonic选择应该没问题,只需使用Where代替WhereExpression(你得到什么SQL?)。

我还建议使用SubSonic的强类型列而不是魔术字符串 - 这是使用SubSonic的优势之一。

答案 1 :(得分:1)

烧掉我的赌注,但是当它到达这一点时,我通常使用SqlConnection对象直接传递SQL。我不确定SubSonic 2是否符合这些复杂性。

我也不认为您在亚音速查询中使用的括号实际上正在做任何事情。它们可能会影响条件的解析顺序,但不会影响最终SQL语句的构造(至少不是以合理可控的方式)。

SubSonic 3带来了AndAlso运算符来模拟括号,但即使这样也很粗糙。 LINQ(在SubSonic 3中受支持)可能是唯一可靠的方法。

答案 2 :(得分:0)

我现在无法测试,但请查看此查询是否有效:

new Select("SalesRep, Location, InvoiceNumber, PONumber, POReceivedOn, SurgeryDate, Surgeon")
                    .From(VSalesRepCommissionGrouped.Schema)
                    .WhereExpression("SurgeryDate").IsGreaterThanOrEqualTo(BeginDate)
                              .And("SurgeryDate").IsLessThanOrEqualTo(EndDate)
                     .OrExpression("SurgeryDate").IsGreaterThanOrEqualTo(BeginDate.AddMonths(-1))
                              .And("SurgeryDate").IsLessThanOrEqualTo(EndDate.AddMonths(-1))
                              .And("POReceivedOn").IsGreaterThanOrEqualTo(BeginDate)
                    .AndExpression("UserID").In(new[] { 5, 6, 20 })
                    .OrderAsc("SurgeryDate");