GROUP BY GROUPING SETS

时间:2016-02-11 11:01:57

标签: sql oracle11g group-by rollup

我正在编写Oracle SQL查询;我需要计算小计以及我的常规查询结果。 为此,我决定使用GROUP BY分机(GROUPING SETS)

由于隐私问题,我不会分享实际查询。相反,我写的是一个虚构的查询,最能描述我的小计要求

SELECT  
    region,
    country,
    province,
    city,
    SUM(agg_col1) agg_col1,
    SUM(agg_col2) agg_col2
FROM tbl_name
GROUP BY GROUPING SETS(region)

现在我知道上面的查询会给出错误,因为并非所有非聚合列都是GROUP BY表达式的一部分;但这是我陷入困境的实际点,我不知道如何达到预期的效果。我唯一的要求就是在查询结果的同时获得区域明智的小计和大方法。

如果建议您掌握一些详细的阅读材料或视频,我也将不胜感激。

EDIT 假设下面是一些样本数据 我想要区域的总和 例如,考虑以下数据 地区国家省城市Agg 1 Agg 2

r1  c1  p1  ct1 1   1
r1  c1  p1  ct2 1   1
r1  c1  p2  ct1 1   1
r1  c1  p2  ct2 1   1
r1  c2  p1  ct1 1   1
r1  c2  p1  ct2 1   1
r1  c2  p2  ct1 1   1
r1  c2  p2  ct2 1   1
r2  c1  p1  ct1 1   1
r2  c1  p1  ct2 1   1
r2  c1  p2  ct1 1   1
r2  c1  p2  ct2 1   1
r2  c2  p1  ct1 1   1
r2  c2  p1  ct2 1   1
r2  c2  p2  ct1 1   1
r2  c2  p2  ct2 1   1
Along with above 16 rows i need following 3 rows
r1              8   8
r2              8   8
                16  16

2 个答案:

答案 0 :(得分:1)

尝试此查询:

SELECT  
    region,
    max(country),
    max(province),
    max(city),
    SUM(agg_col1) agg_col1,
    SUM(agg_col2) agg_col2
FROM tbl_name
GROUP BY  ROLLUP (region)

最大值基本上是为了避免你必须将这些列放在组中的错误,它将选择最大值。您可以将其更改为min,或者如果您想要特定值告诉我,我会调整它..

按汇总分组基本上会给你总排。

你的解释不是很好,所以请告诉我你的意思。

答案 1 :(得分:1)

我必须承认我没有GROUPING SETS的经验,所以我不知道这是否会提供一个好的解决方案,而不是。

通常,您需要使用ROLLUP构建总计。然后,您可以在HAVING上应用GROUPING(x)条款,从结果中排除小计:

SELECT  
  region,
  country,
  province,
  city,
  SUM(agg_col1) agg_col1,
  SUM(agg_col2) agg_col2
FROM tbl_name
GROUP BY ROLLUP(region, country, province, city)
HAVING GROUPING(country) = GROUPING(provice) AND GROUPING(country) = GROUPING(city)
ORDER BY region, country, province, city;

如果您想在查询结尾处使用总计,请将ORDER BY子句更改为:

ORDER BY GROUPING(country), region, country, province, city;

BTW:在HAVING子句中,我们要确保三个值都保持相同的值(全0或全1)。没有像ALL_EQUAL(a,b,c)之类的功能,所以我使用了两个与AND相结合的比较。但是,如果您发现它更具可读性,则可以将HAVING子句更改为:

HAVING GROUPING(country) = ALL( GROUPING(provice) , GROUPING(city) )