【问题标题】:Group by for total price against item in multiple categories针对多个类别中的项目的总价分组
【发布时间】:2020-10-04 17:19:53
【问题描述】:

考虑以下数据:

Items | Price | Categories
--------------------------
Item1 |    10 | Cat1, Cat2
Item2 |    20 | Cat1, Cat3
Item3 |    15 | Cat1, Cat2
--------------------------
Total |    45

如果我根据类别对数据进行分组,则会出现以下统计信息

Categories | Price
------------------
Cat1       |    45
Cat2       |    25
Cat3       |    20
------------------
Total      |    90

现在,如果我必须总结价格,实际总和将是 45,但显示的类别的总和会有所不同,即 90。 因此,两种表示都表示不同的统计数据,但它们以自己的方式是正确的。

寻找这个问题的答案:我将如何表示这样的统计数据。例如,Top 的总数为 45,但各个类别的总和为 90。我的意思是,这不会让最终用户感到困惑吗?

除了为每个项目选择一个类别之外,还有其他关于如何解决此问题的建议吗?

【问题讨论】:

    标签: sql database google-bigquery data-handling information-visualization


    【解决方案1】:

    以下是 BigQuery 标准 SQL

    #standardSQL
    SELECT category, SUM(price) AS price FROM (
      SELECT category, price FROM `project.dataset.table`, 
      UNNEST(SPLIT(categories, ', ')) category UNION ALL
      SELECT 'Total', price FROM `project.dataset.table`
    )
    GROUP BY category
    

    如果应用到您的问题中的样本数据,如下例所示

    #standardSQL
    WITH `project.dataset.table` AS (
      SELECT 'Item1' AS item, 10 AS price, 'Cat1, Cat2'  AS categories UNION ALL
      SELECT 'Item2', 20, 'Cat1, Cat3' UNION ALL
      SELECT 'Item3', 15, 'Cat1, Cat2' 
    )
    SELECT category, SUM(price) AS price FROM (
      SELECT category, price FROM `project.dataset.table`, 
      UNNEST(SPLIT(categories, ', ')) category UNION ALL
      SELECT 'Total', price FROM `project.dataset.table`
    )
    GROUP BY category   
    

    结果是

    Row category    price    
    1   Cat1        45   
    2   Cat2        25   
    3   Cat3        20   
    4   Total       45     
    

    总价值正确

    【讨论】:

    • 感谢您的回答。但我想要代表的答案。就像我将如何代表这样的统计数据。例如,Top 的总数为 45,但各个类别的总和为 90。我的意思是,这不会让客户感到困惑吗?
    • 而不仅仅是“Total” - 您可以使用更具描述性的内容来解决潜在的混淆问题。例如“总库存成本”等
    【解决方案2】:

    您可以拆分数据然后重新聚合:

    with t as (
          select 'Item1' as item, 10 as price, 'Cat1, Cat2'  as categories union all
          select 'Item2', 20, 'Cat1, Cat3' union all
          select 'Item3', 15, 'Cat1, Cat2' union all
          select 'Total', 45, NULL
         )
    select coalesce(category, 'Total'), sum(price)
    from t cross join
         unnest(split(t.categories, ', ')) category
    group by rollup(category)
    order by category nulls last;
    

    如果您不需要总数,则删除rolllup

    【讨论】:

    • 感谢您的回答。但我想要代表的答案。就像我将如何代表这样的统计数据。例如,Top 的总数是 45,但各个类别的总和是 90。我的意思是,这不会让客户感到困惑吗?
    • @Umer 。 . .我不知道你的评论指的是什么。这会产生一个总数为 90 的结果。
    猜你喜欢
    • 2020-11-20
    • 1970-01-01
    • 2012-08-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多