大家来学数据库(非学院派,实战派修炼法)

之前提过,很长时间以来,非IT专业学生基本都不学数据库,甚至连选修的机会都没有。倒是没有技术含量的办公自动化大行其道,导致当今绝大多数白领都只会玩Excel之类的傻瓜机,这是白领工作效率低下的重要原因,也是后来者有望弯道超车的好机会。

不过即使真的开数据库课程,也未必是好事。数据库如果按照大家熟悉的学院派教法,估计很多人会从兴致盎然到兴味索然甚至苦不堪言。我们不妨另辟蹊径,来一场实战派修炼。也许大家会惊讶地发现,原以为数据库很难,没想到可以这么简单!

怎么开发数据库管理系统,那是大佬的事。微软的SQL SERVER是现在主流的数据库,我们说的学数据库,只是学习在上面开发自己的应用,难度并不高。如果把SQL SERVER比作巨人,那SQL语言就是阿拉丁的神灯,只要学会SQL语言,就可以指挥巨人呼风唤雨移山填海。SQL语言是所有跟计算机打交道的语言中最接近自然语言的,对于英语基础不错的大学生来说,简直就是大白话(哑巴英语也可以派上大用场了)。因此,我们的实战派修炼,不谈理论,也不谈概念,直接从SQL语言切入。
楼主 久依沙盘  发布于 2019-08-05 17:38:06 +0800 CST  
考虑到大家多半没有安装SQL SERVER,我们就举最简单的例子,从最容易的SQL语句开始,配上结果图,让大家慢慢找感觉。等有了兴趣,再做深入学习的打算。现在这里已经创建好了一张表A1,只有一个字段Z1(数值型),里面只有简单的几个数字。到底里面有些什么?在Excel里,打开一个文件,点开某个工作表,就可以看到内容,对数据库来说,提取表的内容,要这样下指令:

Select Z1 from A1

意思是从A1表中取Z1字段。有些人可能一说写语句就发怵,以为很难很高深,但你看看这个语句,是不是就跟大白话差不多?


楼主 久依沙盘  发布于 2019-08-05 21:23:22 +0800 CST  
第2张表A2也只有1个字段Z2,数据更少。


楼主 久依沙盘  发布于 2019-08-05 21:30:38 +0800 CST  
有了这2张最简单的表,我们就可以开讲数据库中最重要的操作——连接。很多人一开始就把连接想歪了,以为连接就是以一张表中的特征值到另一张表中取相关的属性值,比如用产品的代码到产品表中取它的名称及大小重量等属性。一一对应找东西确实是连接的一种用法,却不是连接的本意。连接的本意是交叉配对,就是说一张表的每一条记录都跟另一张表的每一条记录进行配对,这里A1表8条记录,A2表5条记录,交叉连接的结果是8*5=40条,这没什么。如果两张表各有上千,结果就超过百万条,那就很可怕了。因此交叉连接实际几乎不会用到,但理解了它才真正领悟到数据库的精髓。交叉连接的标准写法是:
select Z1,Z2 from A1 cross join A2,
相信大家会更喜欢更简洁的偷懒写法:
select Z1,Z2 from A1,A2(中间用逗号代替)

结果40条有点太多,只截取头尾2张图,中间大家脑补:




楼主 久依沙盘  发布于 2019-08-05 22:24:03 +0800 CST  
*代表所有表的所有字段。

如果前面有表名加点,则表明是该表的所有字段。

因此,select * from A1,A2 跟上面的 select Z1,Z2 from A1,A2 是等价的,就不配图了。

同理,select A1.* from A1,A2 相当于 select Z1 from A1 重复5遍
楼主 久依沙盘  发布于 2019-08-05 22:35:55 +0800 CST  
select * from A1 join A2 on A1.Z1=A2.Z2

这就是大家最熟悉,最常用的连接方式——内连接,也是默认的连接方式。。

与Excel里Vlookup不同的是,如果找不到A2表的对应记录,A1表的记录也会消失,这是初学者应该特别注意的。

很多初学者往往比照Vlookup来想象连接,默认的内连接恰好与之不同。连接方式用错必定导致报表结果出错。这是入门时期的常见问题,切记切记!



楼主 久依沙盘  发布于 2019-08-05 22:44:19 +0800 CST  
我们再看一种写法:
楼主 久依沙盘  发布于 2019-08-06 06:54:38 +0800 CST  
我们再看一种写法:

select * from A1,A2 where A1.Z1=A2.Z2

这是前面提到的交叉连接加上条件,结果与刚才的内连接完全相同。

内连接与交叉连接加上相应的条件结果相同,这可以帮助我们理解,交叉连接才是连接的源头,内连接尽管用得更多,也尊为默认连接方式,但其实是由交叉连接加条件派生出来的。

where 后面带的是整个语句的条件,on 后面带的是2表间的连接条件,如果多个表连接,就会有多个on。

表间连接条件跟整体条件基本上等价,使用表间连接条件可以使关系更清晰,也使得整体条件不至于太杂乱。
楼主 久依沙盘  发布于 2019-08-06 06:59:12 +0800 CST  
select * from A1 left join A2 on A1.Z1=A2.Z2

这个是左连接,也很常用。

左连接不是默认连接,却是最符合Excel玩家习惯和想象的连接方式。很像那个著名的vlookup函数的表现。

它的意思是,不论是否找到与之匹配的对应记录,反正左表的记录全都要,没有匹配上的右表字段,只能放空(用空值表示),但不会报错,这一点与vlookup不同。




楼主 久依沙盘  发布于 2019-08-06 07:04:23 +0800 CST  
介绍新的连接方式之前,先引入一张新表A3,A3也只有一个字段Z3,数据跟表A1有一定错位。



楼主 久依沙盘  发布于 2019-08-06 10:27:15 +0800 CST  
有左连接,那么也应该有右连接。

右连接跟左连接正好相反,以右表为主表

因为左右表可自由调换,一般习惯上把主表放在左边,使用左连接。右连接相对用得少些(不排除有些人习惯使用右连接,不是还有左撇子么)。在多表连接时,有时候可能需要左右开弓,不过不建议把连接弄得很复杂,不如分步走。玩数据库,分步走是非常重要的基本策略,这个稍后再说。右连接就是把 left 改成 right,很简单:

select * from A1 right join A3 on A1.Z1=A3.Z3


楼主 久依沙盘  发布于 2019-08-06 10:40:45 +0800 CST  
select * from A1 full join A3 on A1.Z1=A3.Z3

这是最后一种连接方式——全连接,全连接就是不论是否对上号,左右两边一个都不能少,这应该也很好理解。

全连接往往被人忽略,需要的时候其实很好用。

对不知道有此连接方式的人来说,用变通方式实现这种效果,是要费些周折的。

连接是数据库的基础,对连接理解不清容易犯低级错误,不过也就这几个类型,没有多大难度。开始不要着急,把连接理解透彻,后面就好走多了。

连接是数据库的核心,也就这5种类型,最常用的其实就内连接与左连接,理解了连接,数据库的大门就已经敞开了。芝麻开门,数据库,我来了!


楼主 久依沙盘  发布于 2019-08-06 10:52:18 +0800 CST  
select *,Z1+Z3 as [Z1+Z3] from A1 full join A3 on A1.Z1=A3.Z3

现在开讲字段运算。

连接后,不仅可以取任意表的任意字段,还可以对字段进行运算。表达方式是:先写公式,中间加 as,后面是新字段名。as 可以省略,字段名如果包含特殊字符或全数字,要加中括号,普通的字段名可以不加。

这里Z1、Z3都是数值型,因此加号就是相加的意思。可以使用 + - * /(加减乘除)各种运算符号,也可以使用函数。SQL Server 的内置函数没通常的编程语言多,勉强够用。

可能你注意到,结果中只有2表都有的才加和,任何一表没有就空白。这就是前面所说的空值及空值的运算特点。其实相加动作没有少,只是空值跟什么相加都是空值。初学者一定要特别注意。


楼主 久依沙盘  发布于 2019-08-06 10:58:14 +0800 CST  
select *,isnull(Z1,0)+isnull(Z3,0) [Z1+Z3] from A1 full join A3 on A1.Z1=A3.Z3

为解决空值的困扰,可以用 isnull 函数,把空值转为0,这样相加就没问题了。

Isnull 函数,前面的参数是原值或字段,后面是对应值,可以是0,也可以是其它数字或文本。意思是,如果原值不是空值,就保持不变,如果是空值,就转变成对应值。


楼主 久依沙盘  发布于 2019-08-06 11:07:14 +0800 CST  
select *,isnull(cast(Z1 as varchar(10)),'')+isnull(cast(Z3 as varchar(10)),'') [Z1Z3] from A1 full join A3 on A1.Z1=A3.Z3

对于文本来说,加号就表示拼接或相连。

Cast 函数表示转换类型,as 前面是原值或字段,后面是转换成的类型。

Varchar 表示变长度文本类型,括号内的数字是最大长度。如果长度小于最大长度,实际多少就多少,如果超出最大长度,也不报错,只返回星号(*)



楼主 久依沙盘  发布于 2019-08-06 11:35:48 +0800 CST  
select Z1,sum(Z2) SZ2 from A1,A2 group by Z1

分组汇总是很有用也很常用的功能。表示以Z1为分组依据,把Z2汇总。这有点类似于 Excel 里的 sumif 函数。每个 sumif 函数的结果约当于这里的一条。

由于采用交叉连接的结果作为原始数据,汇总值完全相同显得有些无趣。一般来说不会是这样整齐划一的。


楼主 久依沙盘  发布于 2019-08-06 13:59:11 +0800 CST  
select Z1,sum(Z2) SZ2,count(Z2) CZ2,min(Z2) MZ2,max(Z2) XZ2 from A1,A2 group by Z1

除了 sum,count 表示计数,min 表示最小,max 表示最大,都很好理解。Count 还比较常用,后两个就用得少些。



楼主 久依沙盘  发布于 2019-08-06 14:02:43 +0800 CST  
select Z2,sum(Z2) SZ2,count(Z2) CZ2,min(Z2) MZ2,max(Z2) XZ2 from A1,A2 group by Z2

如果把分组依据换成Z2,结果就大不一样了。


楼主 久依沙盘  发布于 2019-08-06 14:08:08 +0800 CST  
关于SQL语句的实例,后续还将不断推出。其实只要很好理解了以上的语句,数据库的基础就打下了,看到相关代码就不会觉得是天书了。当然光凭这些简单的例子还算不上实战,应该做点实际的应用才算。做什么呢?现在手机不离手,我们就做个APP吧。详见新帖《一起来做APP.001》。
楼主 久依沙盘  发布于 2019-08-08 08:08:12 +0800 CST  
不知为何,没排序前,10竟然排到9前面。

我们如果希望按顺序,那就使用排序功能,order by 后面加上字段名,多个中间加逗号,排在前面的优先。

但是结果有点意外,9、10虽然规矩了,但居然跑到最前面。这是因为Z1为空,空值最小,所以数据库没有错,是我们没考虑周全。

楼主 久依沙盘  发布于 2019-08-11 07:18:37 +0800 CST  

楼主:久依沙盘

字数:4941

发表时间:2019-08-06 01:38:06 +0800 CST

更新时间:2019-08-16 17:54:20 +0800 CST

评论数:32条评论

帖子来源:天涯  访问原帖

 

热门帖子

随机列表

大家在看