写sql的思路不同于常规编程语言(C、python)等等。前者,考虑如何一步步地得到最终答案;后者,考虑如何一步步地收缩数据范围。
简而言之,前者是面向过程化(for each row do x),后者是面向集合(do all -> another all)。
具体来讲,写sql从两种角度考虑:
一、集合
- 首先考虑,要得到正确结果,需要把哪些表,以何种形式连接起来;
- 对连接之后的大集合,做怎么样的过滤 (where、having)
- 根据需要做出合适的投影 (select)
- 可能需要重复前面三步
select T1.x, T1.y
from T1 left outer join T2
where T1.z = T2.z
二、变量替换
传统语言,变量部分要么用变身本身,要么用函数代替。如 a = b; a = f(b)
1、变量部分可以用子查询代替
sql语句的任意一部分(select、from、where、having)都可以用子查询去做,比如
select:这地方的子查询必须是标量子查询(明确返回只有一个值的集合,如sum(x)等)
from:select x from (select ...) tmp_table ...
where: exist(select ...)、 in (select ...)
having:比较符号(〉〈)后面跟的,肯定也只能是标量子查询
2、变量部分也可以用语句代替
表内容:
2005-05-09 胜
2005-05-09 胜
2005-05-09 负
2005-05-09 负
2005-05-10 胜
2005-05-10 负
2005-05-10 负
如果要生成下列结果, 该如何写sql语句?
胜 负
2005-05-09 2 2
2005-05-10 1 2 select rq, sum(case when shengfu='胜' then 1 else 0 end)'胜',
sum(case when shengfu='负' then 1 else 0 end)'负'
from #tmp
group by rq