mysql之路第二篇
不会一两个数据库怎么行
- 查询简介
- 去重
- 条件
- 聚合
- 分组
- 排序
- 分页
- 总结与小尝试
一、查询简介
第一篇中就简单的涉及了查询的一般语法:
SELECT * FROM 表名;
- from关键字跟着表名,表示数据来源于这张表
- select后面写表中的列名,如果是*表示在结果中显示表中所有列
- 在select后面的列名部分,可以使用as为列起别名,这个别名出现在结果集中
- 如果要查询多个列,之间使用逗号分隔
二、 去重
SELECT 指令让我们能够读取表格中一个或数个栏位的所有资料。这将把所有的资料都抓出,无论资料值有无重复。在资料处理中,我们会经常碰到需要找出表格内的不同资料值的情况。换句话说,我们需要知道这个表格/栏位内有哪些不同的值,而每个值出现的次数并不重要。这要如何达成呢?在 SQL 中,这是很容易做到的。我们只要在 SELECT 后加上一个 DISTINCT 就可以了。DISTINCT 的语法如下:
SELECT DISTINCT "栏位名" FROM "表格名";
找出所有不同的Address:
SELECT DISTINCT Address FROM Customer;
三、 条件
我们并不一定每一次都要将表格内的资料都完全抓出。在许多时候,我们会需要选择性地抓资料。我们就需要用到 WHERE 这个指令。这个指令的语法如下:
SELECT "栏位名" FROM "表格名" WHERE "条件";
找出City为BJ所有的First_Name:
SELECT First_Name FROM Customer WHERE City='BJ';
1、 比较运算符
- 等于 =
- 大于 >
- 大于等于 >=
- 小于 <
- 小于等于 <=
- 不等于!=或<>
2、 逻辑运算符
- and
SELECT First_Name FROM Customer WHERE NOT City='BJ' AND Address='CN';
- or
SELECT First_Name FROM Customer WHERE NOT City='BJ' OR Address='CN';
- not
SELECT First_Name FROM Customer WHERE NOT First_Name ='xu';
3、 模糊查询
LIKE 是另一个在 WHERE 子句中会用到的指令。基本上,LIKE 能让我们依据一个套式 (pattern) 来找出我们要的资料。LIKE这个指令的语法如下:
SELECT "栏位名" FROM "表格名" WHERE "栏位名" LIKE {套式};
常用{套式} ,%表示任意多个字符,_表示一个任意字符,以下是几个例子:
- ‘A_Z’: 所有以 ‘A’ 起头,另一个任何值的字原,且以 ‘Z’ 为结尾的字串。 ‘ABZ’ 和 ‘A2Z’ 都符合这一个模式,而 ‘AKKZ’ 并不符合 (因为在 A 和 Z 之间有两个字原,而不是一个字原)
- ‘ABC%’: 所有以 ‘ABC’ 起头的字串。举例来说,’ABCD’ 和 ‘ABCABC’ 都符合这个套式
- ‘%XYZ’: 所有以 ‘XYZ’ 结尾的字串。举例来说,’WXYZ’ 和 ‘ZZXYZ’ 都符合这个套式。
- ‘%AN%’: 所有含有 ‘AN’ 这个套式的字串。举例来说, ‘LOS ANGELES’ 和 ‘SAN FRANCISCO’ 都符合这个套式。
4、 范围查询
- in 表示在一个非连续的范围内
SELECT "栏位名" FROM "表格名" WHERE "栏位名" IN ('值一', '值二', ...);
SELECT * FROM Customer WHERE First_Name IN ('xu', 'wang');
- between…and… 表示在一个非连续的范围内
SELECT "栏位名" FROM " 表格名" WHERE "栏位名" BETWEEN '值一' AND '值二';
SELECT * FROM Customer WHERE SID BETWEEN 1 AND 6;
5、 空判断
- null与””是不同的
- 判断空:is null
SELECT * FROM Customer WHERE City IS NULL;
- 判断非空:is not null
SELECT * FROM Customer WHERE City IS NOT NULL;
6、 优先级
- 小括号(),NOT,比较运算符,逻辑运算符
- AND 比 OR 先运算,如果同时出现并希望先算OR,需要结合()使用
四、 聚合
- 为了快速得到统计数据,提供了5个聚合函数
运用函数的语法是:
SELECT "函数名"("栏位名") FROM "表格名";
- count(*)表示计算总行数,括号中写星与列名,结果是相同的
SELECT COUNT(*) FROM Customer;
- AVG(*)表示计算平均值
SELECT AVG(SID) FROM Customer;
- MIN(*)表示计算最小值
SELECT MIN(SID) FROM Customer;
- MAX(*)表示计算最大值
SELECT MAX(SID) FROM Customer;
- SUM(*)表示计算总和
SELECT SUM(SID) FROM Customer;
五、 分组
- 按照字段分组,表示此字段相同的数据会被放到一组中
- 分组后,只能查询出相同的数据列,对于有差异的数据列无法出现在结果集中
可以对分组后的数据进行统计,做聚合运算
运用函数的语法是:
SELECT "栏位1", SUM("栏位2") FROM "表格名" GROUP BY "栏位1";
SELECT City,SUM(SID) FROM Customer GROUP BY City;
如何对聚合函数产生的值来设定条件呢?
HAVING 子句通常是在一个 SQL 句子的最后。一个含有 HAVING 子句的 SQL 并不一定要包含 GROUP BY 子句。HAVING 的语法如下:
SELECT "栏位1", SUM("栏位2") FROM "表格名" GROUP BY "栏位1" HAVING (函数条件);
SELECT Address ,SUM(SID) FROM Customer GROUP BY Address HAVING SUM(SID)>5;
对比WHERE与HAVING:
- WHERE是对FROM后面指定的表进行数据筛选,属于对原始数据的筛选
- HAVING是对GROUP BY的结果进行筛选
六、排序
事实上,我们经常需要能够将抓出的资料做一个有系统的显示。这可能是由小往大 (ascending) 或是由大往小 (descending)。在这种情况下,我们就可以运用 ORDER BY这个指令来达到我们的目的。ORDER BY 的语法如下:
SELECT "栏位名" FROM "表格名" [WHERE "条件"] ORDER BY "栏位名" [ASC, DESC];
如果 WHERE 子句存在的话,它是在 ORDER BY 子句之前。ASC 代表结果会以由小往大的顺序列出,而 DESC 代表结果会以由大往小的顺序列出。如果两者皆没有被写出的话,那我们就会用 ASC。
可以照好几个不同的栏位来排顺序,在这个情况下,ORDER BY 子句的语法如下(假设有两个栏位):
ORDER BY "栏位一" [ASC, DESC], "栏位二" [ASC, DESC]
若我们对这两个栏位都选择由小往大的话,那这个子句就会造成结果是依据 “栏位一” 由小往大排。若有好几笔资料 “栏位一” 的值相等,那这几笔资料就依据 “栏位二” 由小往大排。
SELECT First_Name FROM Customer ORDER BY SID DESC;
SELECT First_Name FROM Customer IsDelete=0 ORDER BY SID DESC;
除了栏位名外,我们也可以用栏位的顺序 (依据 SQL 句中的顺序)。在 SELECT 后的第一个栏位为 1,第二个栏位为 2,以此类推。
SELECT First_Name,SID FROM Customer IsDelete=0 ORDER BY SID DESC;
七、分页
- 当数据量过大时,在一页中查看数据是一件非常麻烦的事情
- 语法
SELECT * FROM 表名 limit start,count
- 从start开始,获取count条数据
- start索引从0开始
例子:分页
- 已知:每页显示m条数据,当前显示第n页
- 获取总页数:
- 查询总条数p1
- p2=p1/m
- 若整除p2为总页数
- 若不整除p2+1为总页数
- 获取第n页数据
SELECT * FROM Customer WHERE IsDelete=0 LIMIT (n-1)*m,m;
八、总结
- 完整的SELECT语句
SELECT DISTINCT * FROM 表名 WHERE .... GROUP BY .... HAVING ... ORDER BY ... LIMIT START,COUNT
执行顺序为:
- FROM 表名
- WHERE …
- GROUP BY …
- SELECT DISTINCT *
- HAVING
- ORDER BY …
- LIMIT START , COUNT
- 实际使用中,只是语句中某些部分的组合,而不是全部