MySQL 如何使用 CASE 语句作为列而不是行按日期分组

MySQL How to group by date with CASE statements as columns instead of rows

不确定我问的是否正确。 我有一个查询,我试图根据另一个 table 数量值显示每个 reason_id 的总计,然后在 reason_id 存在的 table 中按月分组.

到目前为止我的查询是:

select
month(f.c_date),
case when q.reason_id = 2 then sum(f.produced) else 0 end as 'LowM',
case when q.reason_id = 3 then sum(f.produced) else 0 end as 'LowP',
case when q.reason_id = 4 then sum(f.produced) else 0 end as 'LowSC',

from freeze f
inner join freezeq q on f.id = q.frz_id
inner join location l on f.t_id = l.id

where 1=1
and f.c_date like '%2018%'
group by q.reason_id, month(f.c_date);

我需要删除 "group by q.reason_id" 但当然 SUM 值不会分开。

我正在尝试将 CASE 显示为列和 f.produced 值的 SUM,但在 f.c_date.

上分组

我尝试了几种不同的子查询方法,但似乎无法理解。

感谢集体思想能给我的任何帮助!

谢谢!

您似乎想使用条件聚合函数,在sum函数中使用case when

select
    month(f.c_date),
    sum(case when q.reason_id = 2 then f.produced) else 0 end) as 'LowM',
    sum(case when q.reason_id = 3 then f.produced else 0 end) as 'LowP',
    sum(case when q.reason_id = 4 then f.produced else 0 end) as 'LowSC'
from freeze f
inner join freezeq q on f.id = q.frz_id
inner join location l on f.t_id = l.id
where  f.c_date like '%2018%'
group by  month(f.c_date);

注意

我删除了 1=1 and,因为您的查询中没有任何意义。

我想你问的是如何进行条件聚合

将聚合移动到条件之外。条件将 return 我们要聚合的标量(如果满足条件)或 return 0 或 NULL(如果不满足条件)。聚合函数将在 returned 标量上运行。

替换为:

  case when q.reason_id = 2 then sum(f.produced) else 0 end as 'LowM'

有了这个:

  SUM( CASE WHEN q.reason_id = 2 THEN f.produced ELSE 0 END ) AS `LowM`

其他说明:

如果 c_date 是 DATE、DATETIME 或 TIMESTAMP 数据类型,

替换此条件:

    f.c_date LIKE '%2018%' 

    f.c_date >= '2018-01-01'
AND f.c_date  < '2018-01-01' + INTERVAL 1 YEAR

这将使 MySQL 在 suitable 索引上使用范围扫描操作(如果 suitable 索引可用。)

在 DATE 上使用 LIKE 比较将强制 MySQL 评估 table 中的 每个 行,以转换每个 c_date 将值转换成字符串,并进行字符串比较。

(我们可能希望优化器 "smart" 足以找出更有效的重写,但它并不是那么聪明。)


WHERE 1=1 对性能没有任何影响。我们经常在动态生成的 WHERE 子句中看到这一点;应用程序代码可以只附加 AND whatever,而不是检查我们是否需要 WHERE 关键字来代替 AND(对于 WHERE 子句中的第一个条件) .)

任何被 WHERE 1=1 搞糊涂的新手都可以很容易地上手。