当既要分组又要转置时,case when前必须使用max()等聚合函数
下面以一个题为例:
#成绩表
CREATE TABLE `cjb` (
`xuehao` int(11) DEFAULT NULL,
`kemu` varchar(20) DEFAULT NULL,
`chengji` int(11) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
INSERT into cjb(xuehao,kemu,chengji) values (1,'语文',80);
INSERT into cjb(xuehao,kemu,chengji) values (2,'语文',66);
INSERT into cjb(xuehao,kemu,chengji) values (1,'数学',60);
INSERT into cjb(xuehao,kemu,chengji) values (2,'数学',72);
#学籍表
CREATE TABLE `xjb` (
`xuehao` int(11) DEFAULT NULL,
`xingming` varchar(20) DEFAULT NULL,
`banji` int(11) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
INSERT into xjb(xuehao,xingming,banji) values (1,'张三',1);
INSERT into xjb(xuehao,xingming,banji) values (2,'李四',2);
select xjb.xuehao as '学号'
,xingming as '姓名'
,(case when kemu = '语文' then chengji end) as '语文'
,(case when kemu = '语文' then chengji end) as '数学'
,sum(chengji) as '总分'
from cjb left join xjb on cjb.xuehao = xjb.xuehao
group by xjb.xuehao
,xingming
,(case when kemu = '语文' then chengji end)
,(case when kemu = '语文' then chengji end)
order by xjb.xuehao
,xingming;
不加聚合函数时,意味case when语句会出现在group by中,这样会导致按学科分组,Null和分数将分在不同行。
——
(补充:其中 左连接left join 和 内连接join 都可以,但是左连接可以减少数据量,尽量选用左连接)
select xjb.xuehao as '学号'
,xingming as '姓名'
,max(case when kemu = '语文' then chengji end) as '语文'
,max(case when kemu = '数学' then chengji end) as '数学'
,sum(chengji) as '总分'
from cjb left join xjb on cjb.xuehao = xjb.xuehao
group by xjb.xuehao
,xingming
order by xjb.xuehao
,xingming;
加聚合函数时,不会按case when语句分组。
——
(补充:这种情况用 sum() 和 max() 都可以,但是如果case when的数据有重复,则不能用sum()。)