2017-02-28 74 views
1

我有一個相當複雜的查詢使用GROUPING SETS執行一些聚合,它看起來大致如下所示:僅返回前n個結果各組GROUPING SETS查詢

SELECT 
    column1, 
    [... more columns here] 
    count(*) 
FROM table_a 
GROUP BY GROUPING SETS (
    column1, 
    [... more columns here] 
) 
ORDER BY count DESC 

這工作相當不錯,在一般情況下,只要每組的結果數量相當小。但是我在這個查詢中有一些列可以有大量不同的值,這會導致這個查詢返回大量的行。

我實際上只對分組集合中每個組的最高結果感興趣。但是,在使用分組集的查詢中,似乎沒有明顯的方式來限制每個組的結果數量,在這種情況下LIMIT不起作用。

我使用的是PostgreSQL 9.6,所以我沒有限制我可以在這裏使用哪些新功能。

所以我的查詢做什麼是這樣的:

| column1 | column2 | count | 
|---------|---------|-------| 
| DE  |   | 32455 | 
| US  |   | 3445 | 
| FR  |   | 556 | 
| GB  |   | 456 | 
| RU  |   | 76 | 
|   | 12  | 10234 | 
|   | 64  | 9805 | 
|   | 2  | 6043 | 
|   | 98  | 2356 | 
|   | 65  | 1023 | 
|   | 34  | 501 | 

我真正想要的是什麼,只返回前3個結果:

| column1 | column2 | count | 
|---------|---------|-------| 
| DE  |   | 32455 | 
| US  |   | 3445 | 
| FR  |   | 556 | 
|   | 12  | 10234 | 
|   | 64  | 9805 | 
|   | 2  | 6043 | 
+0

什麼是您的SELECT子句中的「分組」?這是正確的語法postgres? –

+0

另外'分組集'給出了不同的行,所以當你說「每個組的最佳結果」時,你的意思是什麼?請向我們展示樣品數據和例外數據。 –

+0

@OtoShavadze @OtoShavadze是一個Postgres特定的函數,用於對集合進行分組以確定該行屬於哪些集合,但實際上並不需要這個最小的示例,所以我只是將其刪除以避免混淆。我還添加了示例輸出。 –

回答

2

使用row_numbergrouping

select a, b, total 
from (
    select 
     a, b, total, 
     row_number() over(
      partition by g 
      order by total desc 
     ) as rn 
    from (
     select a, b, count(*) as total, grouping ((a),(b)) as g 
     from t 
     group by grouping sets ((a),(b)) 
    ) s 
) s 
where rn <= 3 
1

事情是這樣的:

WITH T(column1 , column2, cnt) AS 
(
SELECT 'kla', 'k', 10 
UNION ALL 
SELECT 'kle', 'm', 30 
UNION ALL 
SELECT 'foo', 'k', 10 
UNION ALL 
SELECT 'bar', 'm', 30 
UNION ALL 
SELECT 'bar', 'k', 20 
UNION ALL 
SELECT 'foo', 'm', 15 
UNION ALL 
SELECT 'foo', 'p', 10 
), 
tt AS (select column1, column2, COUNT(*) AS cnt from t GROUP BY GROUPING SETS((column1), (column2)) ) 

(SELECT column1, NULL as column2, cnt FROM tt WHERE column1 IS NOT NULL ORDER BY cnt desc LIMIT 3) 
UNION ALL 
(SELECT NULL as column1, column2, cnt FROM tt WHERE column2 IS NOT NULL ORDER BY cnt desc LIMIT 3)