读SQL进阶教程笔记01_CASE表达式 今日报
1.概述
1.1.SQL-92标准里加入的最有用的特性
1.2.写法
(相关资料图)
1.2.1.简单CASE表达式
CASE sexWHEN "1" THEN ’男’WHEN "2" THEN ’女’ELSE ’其他’ END
- 1.2.1.1.写法简单,但能实现的事情比较有限
1.2.2.搜索CASE表达式
CASE WHEN sex ="1"THEN’男’WHEN sex ="2"THEN’女’ELSE ’其他’ END
1.2.2.1.简单CASE表达式能写的条件,搜索CASE表达式也能写
1.2.2.2.可以使用BETWEEN、LIKE和<、>等便利的谓词组合,以及能嵌套子查询的IN和EXISTS谓词
1.2.2.3.CASE表达式用在SELECT子句里时,既可以写在聚合函数内部,也可以写在聚合函数外部
1.2.2.3.1.CASE表达式在执行时会被判定为一个固定值,因此它可以写在聚合函数内部
1.2.2.3.2.因为它是表达式,所以还可以写在SELECE子句、GROUP BY子句、WHERE子句、ORDER BY子句里
1.2.2.4.是支撑SQL声明式编程的根基之一,也是灵活运用SQL时不可或缺的基础技能
1.2.2.4.1.在能写列名和常量的地方,通常都可以写CASE表达式
1.3.注意事项
1.3.1.统一各分支返回的数据类型
- 1.3.1.1.某个分支返回字符型,而其他分支返回数值型的写法是不正确的
1.3.2.要注意条件的排他性
1.3.3.不要忘了写END
1.3.4.养成写ELSE子句的习惯
1.3.4.1.ELSE子句是可选的
1.3.4.2.不写也不会出错
1.3.4.2.1.不写可能会造成“语法没有错误,结果却不对”这种不易追查原因的麻烦
1.3.4.3.即便是在结果可以为NULL的情况下
1.4.必须在SELECT子句和GROUP BY子句这两处写一样的CASE表达式
1.5.GROUP BY子句使用的正是SELECT子句里定义的列的别称
1.5.1.这种写法是违反标准SQL的规则的
1.5.1.1.因为GROUP BY子句比SELECT语句先执行
1.5.1.2.所以在GROUP BY子句中引用在SELECT子句里定义的别称是不被允许的
1.5.2.Oracle、DB2、SQL Server等数据库里采用这种写法时就会出错
1.5.3.在PostgreSQL和MySQL中可以顺利执行
1.5.4.不强烈推荐大家使用
2.示例
2.1.
-- 男性人口 SELECT pref_name, SUM(population) FROM PopTbl2 WHERE sex ="1" GROUP BY pref_name; -- 女性人口 SELECT pref_name, SUM(population) FROM PopTbl2 WHERE sex ="2" GROUP BY pref_name;
2.2.
SELECT pref_name, --男性人口 SUM( CASE WHEN sex ="1"THEN population ELSE 0 END) AS cnt_m, --女性人口 SUM( CASE WHEN sex ="2"THEN population ELSE 0 END) AS cnt_f FROM PopTbl2 GROUP BY pref_name;
2.3.能将SQL的查询结果转换为二维表的格式
- 2.3.1.新手用WHERE子句进行条件分支,高手用SELECT子句进行条件分支
3.用CHECK约束定义多个列的条件关系
3.1.
CONSTRAINT check_salary CHECK ( CASE WHEN sex ="2" THEN CASE WHEN salary <= 200000 THEN 1 ELSE 0 END ELSE 1 END = 1 )
- 3.1.1.使用蕴含式,男性也可以在这里工作
3.2.
CONSTRAINT check_salary CHECK ( sex ="2"AND salary <= 200000 )
- 3.2.1.使用逻辑与,该公司将不能雇佣男性员工
4.在UPDATE语句里进行条件分支
4.1.
--条件1 UPDATE Salaries SET salary = salary * 0.9 WHERE salary >= 300000; --条件2 UPDATE Salaries SET salary = salary * 1.2 WHERE salary >= 250000 AND salary < 280000;
4.2.用CASE表达式写正确的更新操作
UPDATE Salaries SET salary = CASE WHEN salary >= 300000 THEN salary * 0.9 WHEN salary >= 250000 AND salary < 280000 THEN salary * 1.2 ELSE salary END;
4.2.1.最后一行的ELSE salary非常重要,必须写上
4.2.2.因为如果没有它,条件1和条件2都不满足的员工的工资就会被更新成NULL
4.3.
--1.将a转换为中间值d UPDATE SomeTable SET p_key ="d" WHERE p_key ="a"; --2.将b调换为a UPDATE SomeTable SET p_key ="a" WHERE p_key ="b"; --3.将d调换为b UPDATE SomeTable SET p_key ="b" WHERE p_key ="d";
4.4.用CASE表达式调换主键值
UPDATE SomeTable SET p_key = CASE WHEN p_key ="a" THEN "b" WHEN p_key ="b" THEN "a" ELSE p_key END WHERE p_key IN ("a", "b");
5.表之间的数据匹配
5.1.表的匹配:使用IN谓词
SELECT course_name, CASE WHEN course_id IN (SELECT course_id FROM OpenCourses WHERE month = 200706) THEN"○" ELSE"×"END AS "6月", CASE WHEN course_id IN (SELECT course_id FROM OpenCourses WHERE month = 200707) THEN"○" ELSE"×"END AS "7月", CASE WHEN course_id IN (SELECT course_id FROM OpenCourses WHERE month = 200708) THEN"○" ELSE"×"END AS "8月" FROM CourseMaster;
5.2.表的匹配:使用EXISTS谓词
SELECT CM.course_name, CASE WHEN EXISTS (SELECT course_id FROM OpenCourses OC WHERE month = 200706 AND OC.course_id = CM.course_id) THEN"○" ELSE"×"END AS "6月", CASE WHEN EXISTS (SELECT course_id FROM OpenCourses OC WHERE month = 200707 AND OC.course_id = CM.course_id) THEN"○" ELSE"×"END AS "7月", CASE WHEN EXISTS (SELECT course_id FROM OpenCourses OC WHERE month = 200708 AND OC.course_id = CM.course_id) THEN"○" ELSE"×"END AS "8月" FROM CourseMaster CM;
- 5.2.1.从性能方面来说,EXISTS更好
6.在CASE表达式中使用聚合函数
6.1.条件1:选择只加入了一个社团的学生
SELECT std_id, MAX(club_id) AS main_club FROM StudentClub GROUP BY std_id HAVING COUNT(*) = 1;
6.2.条件2:选择加入了多个社团的学生
SELECT std_id, club_id AS main_club FROM StudentClub WHERE main_club_flg ="Y";
6.3.
SELECT std_id, CASE WHEN COUNT(*) = 1 --只加入了一个社团的学生 THEN MAX(club_id) ELSE MAX(CASE WHEN main_club_flg ="Y" THEN club_id ELSE NULL END) END AS main_club FROM StudentClub GROUP BY std_id;
关键词:
精心推荐
- 读SQL进阶教程笔记01_CASE表达式 今日报
- 【全球报资讯】深深房A(000029):3月28日北向资金增持29.48万股
- 草乌叶的功效与作用(草乌叶的功效与作用点)
- 祛斑老师有哪些(祛斑老师)_天天关注
- 中级会计证报名入口官网是什么-全球微动态
- 世界快报:成都购车补贴针对的是所有车型吗?
- 焦点滚动:中国第一部动画片是什么动画片_中国第一部动画片是什么?
- 方正控股(00418)发布年度业绩 股东应占溢利3475.1万港元 同比减少20.08% 全球动态
- 阿富汗首都喀布尔发生爆炸袭击已致6人死亡|世界热议
- 世界新资讯:大连海事大学与中国工商银行大连市分行举行共建培训基地及图书馆项目揭牌仪式暨2023年新员工入职培训班开班仪式
- 天天即时:北京论语:如此攀岩谁该汗颜
- 天天微速讯:石壕吏叙事脉络_石壕吏的线索
- 奎克利:队友一直希望我能拿到40+10 不是所有人都有这么棒的队友
- 中国人保卓越保险战略不会改变 大力推进财险业务降本增效
-
工人日报-中工网记者赵昂“我们立足中小学用户特点,做了翔实的产品设计和规划,涉及硬件、课程、研学三大部分,分层、分类打造了三款航天教育
-
85岁的马玉琴怎么也不会想到自己不顾世俗眼光,执意与比自己小好多的李玉成在一起,男方却在自己卧床养病期间另寻新欢?这究竟发生了什么?这
-
为给辖区居民群众提供“零距离”医疗卫生服务,提高居民健康水平,让居民有“医靠”。3月25日,鹤壁经济技术开发区海河路街道北晨社区联合大赉
-
3月27日北向资金减持67 32万股仁和药业。近5个交易日中,获北向资金减持的有3天,累计净减持251 14万股。近20个交易日中,获北向资金增持的有1
-
很多兰州人的一天,都是从一碗牛肉拉面开始的,放眼全国,这碗香喷喷的兰州牛肉拉面更是俘获了无数人的味蕾。近日,由甘肃省政协
X 关闭
X 关闭
产业
-
不用跑北京 在家门口也能挂上顶...
日前,我省首个神经疾病会诊中心——首都医科大学宣武医院河北医院...
-
“十四五”期间 河北省将优化快...
从省邮政管理局获悉,十四五期间,我省将优化快递空间布局,着力构...
-
张家口市宣化区:光伏发电站赋能...
3月19日拍摄的张家口市宣化区春光乡曹庄子村光伏发电站。张家口市宣...
-
“张同学”商标被多方抢注 涉及...
“张同学”商标被多方抢注,官方曾点名批评恶意抢注“丁真” ...
-
山东济南“防诈奶奶团”花式反诈...
中新网济南12月15日电 (李明芮)“老有所为 无私奉献 志愿服...
-
广州新增1例境外输入关联无症状...
广州卫健委今日通报,2021年12月15日,在对入境转运专班工作人...
-
西安报告初筛阳性病例转为确诊病例
12月15日10:20,经陕西西安市级专家组会诊,西安市报告新冠病毒...
-
广东东莞新增本土确诊病例2例 ...
(抗击新冠肺炎)广东东莞新增本土确诊病例2例 全市全员核酸检测...
-
中缅边境临沧:民警深夜出击捣毁...
中新网临沧12月15日电 (胡波 邱珺珲)记者15日从云南临沧边境...
-
“土家鼓王”彭承金:致力传承土...
中新网恩施12月15日电 题:“土家鼓王”彭承金:致力传承土家...