【问题标题】:How to Count the number of rows within each distinct group?如何计算每个不同组中的行数?
【发布时间】:2017-10-06 21:32:55
【问题描述】:

给定以下 MySQL 表:

| id | category | Hour | quantity|
|  0 | Sunday   |  10  |  32    |
|  0 | Sunday   |  11  |  19    |
|  0 | Sunday   |  12  |  48    |
|  0 | Sunday   |  19  |  7     |
|  1 | Monday   |  09  |  45    |
|  1 | Monday   |  10  |  17    |
|  1 | Monday   |  12  |  18    |
|  2 | Tuesday  |  08  |  16    |
|  2 | Tuesday  |  09  |  39    |
|  2 | Tuesday  |  10  |  24    |
|  2 | Tuesday  |  11  |  37    |
|  2 | Tuesday  |  12  |  40    |

我需要计算第五列,它必须是“数量”除以 id 的行数:对于 0,有 4 行,对于 1 3 行,对于 2 5 行。

| id | category | Hour | quantity| avg |
|  0 | Sunday   |  10  |  32    |  8   |
|  0 | Sunday   |  11  |  19    | 4.75 | 
|  0 | Sunday   |  12  |  48    |  12  |
|  0 | Sunday   |  19  |  7     | 1.75 |
|  1 | Monday   |  09  |  45    |  15  |
|  1 | Monday   |  10  |  17    |  5.7 |
|  1 | Monday   |  12  |  18    |   6  |
|  2 | Tuesday  |  08  |  16    | 3.2  |
|  2 | Tuesday  |  09  |  39    | 7.8  |
|  2 | Tuesday  |  10  |  24    | 4.8  |
|  2 | Tuesday  |  11  |  37    | 7.4  |
|  2 | Tuesday  |  12  |  40    |  8   |

如何在 MySQL 查询中获得结果?

第一个表,是这个查询的结果:

 select id, category, Hour, count(*) as quantity
 FROM table_1
 GROUP by id, Hour ORDER by id, Hour;

这是我尝试的,为了获取每个 id 出现的行数,但是我得到一个很大的数字,id=0 出现次数而不是 id=0 上一个查询中的行数:

select  id, Hour,  count(id)  as q
FROM table_1 
GROUP by id 

这是 mySql 5.6。

【问题讨论】:

    标签: mysql count average rows


    【解决方案1】:

    这确实非常丑陋和麻烦,但它是在没有主键的情况下获得结果的唯一方法:

    SELECT 
      t.id, 
      t.category, 
      t.hour, 
      quantity,  
      ROUND(quantity/count,2) AS avg
    FROM table_1 t
        JOIN (SELECT 
                  id, Hour, count(*) as quantity
                 FROM table_1
                GROUP by id, category, Hour) AS qty
        ON t.id = qty.id AND t.hour = qty.hour
    
        JOIN (SELECT
                id, count(distinct hour) as count 
                 FROM table_1
                    GROUP BY id) as counts 
        ON t.id = counts.id
    GROUP BY id, hour;
    

    至少对我来说,它似乎在本地工作,猜测您的原始数据集是什么样的。

    不过,可能还有更简单的方法。

    编辑:在第二次检查中,“数量”子查询并没有真正增加我所看到的,因此可以将其替换为“计数(*)”,从而实现更优化查询:

    SELECT 
      t.id, 
      t.category, 
      t.hour, 
      count(*) as quantity,  
      ROUND(count(*)/count,2) AS avg
    FROM table_1 t
        JOIN (SELECT
                id, count(distinct hour) as count 
                 FROM table_1
                    GROUP BY id) as counts 
        ON t.id = counts.id
    GROUP BY id, hour;
    

    【讨论】:

    • 如果需要我可以使用主键,我没有在表示例上发布但它也有一个唯一的 id。
    • 如果idcategoryhour(或子集)的每个组合都有一个唯一标识符,则它会缩小查询并提供更“稳健”的解决方案
    • 不,没有这样的粒度,每个事务的唯一 id 但对于 id-category-hour,没有这样的唯一 id,这是聚合的。
    【解决方案2】:

    您需要在仅按id 分组的子查询中进行计数。将子查询加入主查询并进行除法。

    SELECT id, category, hour, COUNT(*) AS quantity, COUNT(*)/count AS avg
    FROM table_1
    JOIN (SELECT id, COUNT(DISTINCT hour) AS count
          FROM table_1
          GROUP BY id) AS counts 
        ON table_1.id = counts.id
    GROUP BY table_1.id, table_1.hour
    ORDER BY table_1.id, table_1.hour
    

    【讨论】:

    • 数量也是一个派生字段,您在此答案中忽略了它
    • @ChrisJ 不,不是,它在原始表中。
    • 不,不是。如果您阅读他的问题,原始“表”只是从查询(他提供)的派生表
    • 谢谢,我看错了,我以为那是他试图获取结果表。
    • 你能用示例输入数据制作一个 sqlfiddle 吗?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-07-16
    • 1970-01-01
    • 2012-04-06
    • 2020-04-05
    相关资源
    最近更新 更多