#为什么要用case表达式
case表达式算比较新的函数,且有很多简略版类似函数:decode(Oracle)、if(Mysql)。Joe Celko说,case表达式也许是SQL-92标准里加入的最有用的特性。
- 它能解决更广泛的问题;
- 写法漂亮;
- 不依赖具体数据库技术,也就是说移植性高。
#两种写法
-- 简单语法
case ID
when '111' then 'A'
when '222' then 'B'
else 'C'
end
-- 搜索式语法(更常用)
case
when ID = '111' then 'A'
when ID = '222' then 'B'
else 'C'
end
#注意事项
- 同意分支数据类型,既then后的数据类型和else后的一致;
- 不要忘记写end;
- 完整书写语法,即else没有值也可以null。
#使用场景
*配合聚合函数,列行转换
name | sex | int |
Q | 1 | 33 |
Q | 2 | 44 |
W | 1 | 55 |
W | 2 | 66 |
select name
,sum(case sex when '1' then int else 0 end) as 'A'
,sum(case sex when '2' then int else 0 end) as 'B'
from table
group by name
name | A | B |
Q | 33 | 44 |
W | 55 | 66 |
解析:把sex这列上为“1”对应的int列上的数字拿出来相加,再按name分配到新建列“男”上,第二行同上。(如果不用case函数,你会用什么函数替代呢?)
*利用两张表格创建新表
select course_name
,max(case when 6月 = 0 then 'O' else 'X' end) as '6月'
,max(case when 7月 = 0 then 'O' else 'X' end) as '7月'
,max(case when 8月 = 0 then 'O' else 'X' end) as '8月'
from
(select course_name
,sum(case when `month` = 200706 then o.course_id else 0 end) as '6月'
,sum(case when `month` = 200707 then o.course_id else 0 end) as '7月'
,sum(case when `month` = 200708 then o.course_id else 0 end) as '8月'
from coursemaster c right join opencourses o
on c.course_id = o.course_id
group by course_name ) as A
group by course_name;
(这个函数可以优化:用子查询,你想出哪些方法呢?)
浅浅的解析:括号里的select已经新建了一张表,而外层语法仅仅是把数字换成“O”和“X”。