2

这在标题中真的很难解释,但这是我的一张表:

CATEGORY_ID   COUNT   GROUPING
1             130     H
2              54     B
3             128     C
4              70     D
5              31     E
6              25     F
7              64     A
8              59     F
9              66     B
10             62     E
11            129     C
12             52     G
13             27     A
14            102     A
15            101     C

我正在尝试编写一个查询来获取TOP 5 CATEGORY_ID's,首先按整体排序COUNT,然后基于该组使用该组中的其他CATEGORY_ID's 而不管他们的COUNT. 所以,如果我想TOP 5根据这条规则进行上述操作(我可能解释得有些糟糕),我的结果将是:

CATEGORY_ID   COUNT   GROUPING
6             25      F <-- THE LOWEST COUNT OVERALL
8             59      F <-- THE NEXT LOWEST IN GROUP 'F'
13            27      A <-- THE NEXT LOWEST OVERALL
7             64      A <-- THE NEXT LOWEST IN GROUP 'A'
14            102     A <-- THE NEXT LOWEST IN GROUP 'A'

我在这里和其他地方看了很多(尝试了诸如 RANK()、DENSE_RANK()、GROUPING SETS 之类的东西 - 主要是在黑暗中刺伤)并且到处都是墙壁。

编辑:另外一件事是我需要COUNT随机打破联系。因此,例如,如果COUNT0所有行,则返回的第一组应该是随机的。我已经通过添加NEWID()ORDER BY下面的两个答案中来尝试过这个,但没有运气。

谢谢你。

4

2 回答 2

5
; with groups as (
  select
    grouping,
    min(count) as group_min
  from categories
  group by grouping
)
select top 5 c.category_id, c.count, c.grouping
from categories c
join groups g on c.grouping = g.grouping
order by g.group_min, c.count

Sql 小提琴

编辑:

要在平局的情况下进行随机化,您可以使用row_number()and向每个组添加随机顺序newid()

; with groups as (
  select
    grouping,
    row_number() over (order by newid()) as random,
    min(count) as group_min
  from categories
  group by grouping
)
select top 5
  c.category_id, c.count, c.grouping
from categories c
join groups g on c.grouping = g.grouping
order by g.group_min, g.random, c.count

Sql 小提琴

于 2013-01-29T19:38:31.973 回答
2

更新:使用RANK()而不是ROW_NUMBER(),因此任何并列的记录(例如当所有计数为 0 时)都将具有相同的排名。这允许 order byNEWID()为您提供随机结果。

;WITH CatByCount AS (
    SELECT 
        CATEGORY_ID, 
        COUNT,
        GROUPING,
        RANK() OVER (ORDER BY COUNT) AS ORD
    FROM theTaBle
)
SELECT TOP 5 CATEGORY_ID, COUNT, GROUPING 
FROM (
    SELECT I.CATEGORY_ID, O.ORD, I.COUNT, I.GROUPING
    FROM CatByCount O
    CROSS APPLY (
        SELECT A.CATEGORY_ID, A.COUNT, A.GROUPING
        FROM theTable A
        WHERE A.GROUPING = O.GROUPING
    ) I
) X
ORDER BY X.ORD, X.COUNT, NEWID()

更新了 Sql Fiddle

于 2013-01-29T19:43:51.060 回答