Sqlserver
 sql >> Base de Dados >  >> RDS >> Sqlserver

MSSQL Select Top 10 pontuações vencedoras, incluindo empates e pelo menos um de cada categoria


Como posso ver, você precisa classificar suas linhas de uma maneira mais sofisticada, para que as entradas que são as principais em todas as categorias sejam incluídas, independentemente de seus valores, e as entradas que não são as principais sejam incluídas de acordo com sua classificação geral. classificações.

O que estou prestes a sugerir pode não ser a solução mais eficiente, mas deve funcionar e, se nada mais puder, pode inspirar outra pessoa a criar algo melhor:
WITH ranked1 AS (
  SELECT
    *,
    RankByCategory = DENSE_RANK() OVER (
      PARTITION BY CategoryID
      ORDER BY Score DESC
    )
  FROM YourTable
),
ranked2 AS (
  SELECT
    *,
    FinalRank = DENSE_RANK() OVER (
      ORDER BY
        CASE RankByCategory WHEN 1 THEN 1 ELSE 2 END,
        Score DESC
    )
  FROM ranked1
)
SELECT
  EntryID,
  CategoryID,
  Score
FROM ranked2
WHERE FinalRank <= @top_n
;

O primeiro CTE está classificando as linhas por categorias, permitindo descobrir quais entradas se tornam as primeiras em suas respectivas categorias. O próximo passo (segundo CTE) é obter rankings globais, desta vez levando em consideração se uma entrada é a primeira em sua categoria ou não. Os valores superiores da categoria recebem classificações mais baixas e, portanto, são garantidos para serem incluídos nos resultados finais. (Claro, você precisa ter certeza de que o número de categorias não é maior que o número de valores distintos que você deseja receber na saída.)

Aqui está um exemplo ao vivo no SQL Fiddle Brincar com.