Нахождение top n для каждой уникальной строки - PullRequest
0 голосов
/ 26 октября 2009

Я пытаюсь получить верхние N записей для каждой уникальной строки данных в таблице (я группирую по столбцам b , c и d , столбец a - уникальный идентификатор, а столбец e - это оценка, в которой я хочу получить первую 1 в этом случае).

a    b    c    d    e
2    38   NULL NULL 141
1    38   NULL NULL 10
1    38   1    NULL 10
2    38   1    NULL 1
1    38   1    8    10
2    38   1    8    1
2    38   16   NULL 140
2    38   16   12   140

например. Из этих данных я хотел бы найти следующие строки:

a    b    c    d    e
2    38   NULL NULL 141
1    38   1    NULL 10
1    38   1    8    10
2    38   16   NULL 140
2    38   16   12   140

Может кто-нибудь указать мне правильное направление, чтобы решить эту проблему?

Ответы [ 3 ]

1 голос
/ 26 октября 2009

Ваш пример не показывает, и вы не объясняете, как вы определяете, какая строка является "верхней", поэтому я поставил ?????? в запросе, где необходимо указать столбец ранжирования, например

a desc

например. В любом случае, это именно то, для чего предназначены аналитические функции в SQL Server 2005 и более поздних версиях.

declare @howmany int = 3;
with TRanked (a,b,c,d,e,rk) as (
  select
    a,b,c,d,e,
    rank() over (
      partition by b,c,d
      order by ???????
    )
  from T
)
  select a,b,c,d,e
  from TRanked
  where rk <= @howmany;
0 голосов
/ 26 октября 2009

Я верю, что это сделает то, что вы сказали (расширив идею от здесь ):

select b,c,d,e, 
rank() over 
(partition by b,c,d order by e desc) "rank" 
from t1 where rank < 5

Приветствие.

0 голосов
/ 26 октября 2009

Нули - это боль, но как-то так:

select * from table1 t1
where a in (
  select top 1 a from table1 t2
  where (t1.b = t2.b or (t1.b is null and t2.b is null))
    and (t1.c = t2.c or (t1.c is null and t2.c is null))
    and (t1.d = t2.d or (t1.d is null and t2.d is null))
  order by e desc
  )

или еще лучше:

select * from (
  select *, seqno = row_number() over (partition by b, c, d order by e desc)
  from table1
  ) a
where seqno = 1
...