TSQL从2个条件中选择一行

时间:2012-04-18 11:55:52

标签: tsql sql-server-2005

我有一张这样的表:

ORDER_ID   CODE1   CODE2   CODE3   STATUS
1          '001'   'BIGP'  NULL    4
2          '002'   'BIGP'  NULL    1
3          '001'    NULL   NULL    6
4          '002'    NULL   'L'     1

和第二个表如下:

ADDRESS_ID   ORDER_ID  TYPE   ADD_DATE       CATEGORY
1            1         'K1'   '2010-01-01'   'CLIENT'
2            1         'D1'   '2010-01-02'   'SYSTEM'
3            2         'D2'   '2010-01-02'   'SYSTEM'
4            2         'D2'   '2010-02-01'   'CLIENT'

对于每个订单,我必须做什么:

  • 状态不在(4,6)
  • CODE1 = '002'
  • (code2 = null和code3 = null)或(code2 in('BIGA','BIGP')and code3 = null)或(code2 = NULL and code3 ='L')

我必须选择一个类型为'D2'或'K1'的地址(D2具有更高的优先级,所以如果有2个地址,则一个K1和第二个D2我必须选择D2)。
如果没有任何类型为D2或K1的地址,我必须为该订单选择类别为“客户”的最旧地址。

这就是我创造的:

SELECT TOP 1000 o.order_Id
              , a.Address_Id
              , a.Zip
            --, *
FROM orders o
 address a
    ON a.order_Id = o.order_Id
WHERE
 (a.Type='D2' OR a.Type='K1')
 AND o.Status NOT IN (4, 6)
 AND code1='002'
 AND ((code2 IS NULL AND code3 IS NULL) OR (code2 IN ('BIGA', 'BIGP') AND code3 IS NULL) OR (code2 IS NULL AND code3 = 'L'))

2 个答案:

答案 0 :(得分:3)

您可以使用CROSS APPLY来完成任务,因为它允许使用derived table中的TOP 1 / ORDER BY语句。

SELECT TOP 1000 o.order_Id
              , a.Address_Id
              , a.Zip
            --, *
FROM orders o
CROSS APPLY
(
 select TOP 1
        a.Address_Id,
        a.Zip
   from address a
  WHERE a.order_Id = o.order_Id
  ORDER BY case a.Type 
                when 'D2' then 1 
                when 'K1' then 2 
                else 3 
            end,
        a.ADD_DATE
) a
WHERE
 o.Status NOT IN (4, 6)
 AND code1='002'
 AND ((code2 IS NULL AND code3 IS NULL) OR (code2 IN ('BIGA', 'BIGP') AND code3 IS NULL) OR (code2 IS NULL AND code3 = 'L'))

除此之外,您可以使用每个订单的最小类型加入派生的地址表:

from orders o
inner join address a
  ON a.order_Id = o.order_Id
inner join
(
  select a.order_id, a.Type,
         row_number () over (partition by a.order_id
                             order by case a.Type when 'D2' then 1 
                                                  when 'K1' then 2 
                                                  else 3 
                                       end, 
                                      a.ADD_DATE) rn
    from Address a
   group by a.order_id, a.Type
) onlyOneAddress
  on a.order_id = onlyOneAddress.order_id
 and a.type = onlyOneAddress.type
 and onlyOneAddress.rn = 1

答案 1 :(得分:0)

只需按[Type] desc添加顺序,它将显示高优先级