T-SQL:根据MAX选择列(其他列)

时间:2010-09-09 20:19:24

标签: sql sql-server tsql greatest-n-per-group

我希望有一种简单的方法可以在不使用子查询的情况下执行此操作:

场景:您有“TableA”,其中包含“Key”,“SubKey”和“Value”列。对于给定的“Key”,我需要获得MAX(“SubKey”)的“Value”。

因此,如果表包含行:

KEY SUBKEY VALUE
1   1      100
1   2      200
1   3      300

对于Key = 1,我需要值300.我希望这样做:

SELECT
  VALUE
FROM
  TableA
WHERE
  Key = 1
HAVING
  SubKey = MAX(SubKey)

但那是不行的。有没有办法做这个没有做'WHERE SubKey =(subselect for max subkey)'?

8 个答案:

答案 0 :(得分:49)

使用自联接:

这将返回所有匹配的子键值的值,以防有多个。

SELECT a.value
  FROM TABLE a
  JOIN (SELECT MAX(t.subkey) AS max_subkey
          FROM TABLE t
         WHERE t.key = 1) b ON b.max_subkey = a.subkey
 WHERE a.key = 1

使用RANK& CTE(SQL Server 2005 +):

这将返回所有匹配的子键值的值,以防有多个。

WITH summary AS (
  SELECT t.*,
         RANK() OVER(ORDER BY t.subkey DESC) AS rank
    FROM TABLE t
   WHERE t.key = 1)
SELECT s.value
  FROM summary s
 WHERE s.rank = 1

使用ROW_NUMBER& CTE(SQL Server 2005 +):

这将返回一行,即使有多个具有相同的子键值...

WITH summary AS (
  SELECT t.*,
         ROW_NUMBER() OVER(ORDER BY t.subkey DESC) AS rank
    FROM TABLE t
   WHERE t.key = 1)
SELECT s.value
  FROM summary s
 WHERE s.rank = 1

使用TOP:

这将返回一行,即使有多个具有相同的子键值...

  SELECT TOP 1
         t.value
    FROM TABLE t
   WHERE t.key = 1
ORDER BY t.subkey DESC

答案 1 :(得分:18)

非常简单,没有加入,没有子查询:

 $params['body']['query']['bool']['must'][]['term']['userid'] = $uid;
 $params['body']['query']['bool']['must'][]['term']['categoryid2'] = $pc;

 $params['body']['query']['bool']['must_not'][]['ids']['values'] = [$pid];

如果您需要每个密钥的最大值:

SELECT FIRST_VALUE(Value) OVER (ORDER BY SubKey DESC)
FROM TableA
WHERE Key = 1

答案 2 :(得分:4)

SELECT MAX(Value)
FROM TableA t1
GROUP BY Key, SubKey
HAVING SubKey = (SELECT MAX(SubKey) FROM TableA t2 WHERE t1.Key = t2.Key)
  AND Key = 1

答案 3 :(得分:3)

OMG小马打了大部分的方法。还有一个:

SELECT
    T1.value
FROM
    My_Table T1
LEFT OUTER JOIN My_Table T2 ON
    T2.key = T1.key AND
    T2.subkey > T1.subkey
WHERE
    T2.key IS NULL

T2.key将为NULL的唯一时间是LEFT JOIN中没有匹配项,这意味着没有具有更高子项的行。如果有多个行具有相同(最高)的子键,则会返回多行。

答案 4 :(得分:1)

OMG Ponie' ROW_NUMBER MAX方法在所有方案中效果最佳,因为如果有两个recordset值具有相同的金额,它将不会失败返回比预期更多的记录并打破可能由summary提供的插入。

缺少的一件事是如果必须返回与每个最大值关联的子键,当还有多个键时,如何执行此操作。只需将您的MIN表格加入GROUPWITH summary AS ( SELECT t.*, ROW_NUMBER() OVER(ORDER BY t.subkey DESC) AS rank FROM TABLE t WHERE t.key = 1) SELECT s.* FROM summary s join (select key, min(rank) as rank from summary group by key) sMAX on s.key = sMAX.key and r.rank = sMAX.rank "本身"然后你走吧

{{1}}

答案 5 :(得分:0)

如果你总是只想要一行代表一个键值,而不是一次只需要多个键的答案,那么所有的联接内容都是无用的过度构建。只需使用OMG小马已经给你的TOP 1查询。

答案 6 :(得分:0)

如果使用CTE的多个键:

WITH CTE AS
(
    SELECT key1, key2, MAX(subkey) AS MaxSubkey
    FROM TableA 
    GROUP BY key1, key2
)
SELECT a.Key1, a.Key2, a.Value
FROM TableA a
    INNER JOIN CTE ON a.key1 = CTE.key1 AND a.key2 = CTE.key2 AND
                      a.subkey = CTE.MaxSubkey

答案 7 :(得分:0)

对于GROUP BY查询,要基于另一列的MAX值获取一列的值,您可以执行以下操作:

SELECT
        CASE 
             WHEN MAX(col_C) > 0 THEN MAX(col_D)
             ELSE NULL 
        END     AS col_D_value_when_col_C_MAX
FROM table 
GROUP BY col_A, col_B