参考链接:https://www.runoob.com/mysql/mysql-tutorial.html
《SQL基础教程》 Mick著
1 数据库的概念
1 数据库(Database)是按照数据结构来组织、存储和管理数据的仓库。
每个数据库都有一个或多个不同的 API 用于创建,访问,管理,搜索和复制所保存的数据。
我们也可以将数据存储在文件中,但是在文件中读写数据速度相对较慢,无法多人共享数据,无法提供操作大量数据所需的格式,实 现读写自动化需要编程能力,无法应对突发事故。
2 DBMS的种类
层次数据库(Hierarchical Database,HDB)关系数据库(Relational Database,RDB)面向对象数据库(Object Oriented Database,OODB) XML数据库(XML Database,XMLDB) 键值存储系统(Key-Value Store,KVS)
现在我们使用关系型数据库管理系统(RDBMS)来存储和管理的大数据量。所谓的关系型数据库,是建立在关系模型基础上的数据库,借助于集合代数等数学概念和方法来处理数据库中的数据。
RDBMS 即关系数据库管理系统(Relational Database Management System)的特点:
- 1.数据以表格的形式出现
- 2.每行为各种记录名称
- 3.每列为记录名称所对应的数据域
- 4.许多的行和列组成一张表单
- 5.若干的表单组成database
3 RDBMS的一些术语
- 数据库: 数据库是一些关联表的集合。数据库是将大量数据保存起来,通过计算机加工而成的可以进行高效访问
的数据集合。用来管理数据库的计算机系统称为数据库管理系统(DBMS)。关系数据库通过关系数据库管理系统(RDBMS)进行管理。 - 数据表: 表是数据的矩阵。在一个数据库中的表看起来像一个简单的电子表格。
- 列: 一列(数据元素) 包含了相同的数据, 例如邮政编码的数据。
- 行:一行(=元组,或记录)是一组相关的数据,例如一条用户订阅的数据。
- 冗余:存储两倍数据,冗余降低了性能,但提高了数据的安全性。
- 主键:主键是唯一的。一个数据表中只能包含一个主键。你可以使用主键来查询数据。
- 外键:外键用于关联两个表。
- 复合键:复合键(组合键)将多个列作为一个索引键,一般用于复合索引。
- 索引:使用索引可快速访问数据库表中的特定信息。索引是对数据库表中一列或多列的值进行排序的一种结构。类似于书籍的目录。
- 参照完整性: 参照的完整性要求关系中不允许引用不存在的实体。与实体完整性是关系模型必须满足的完整性约束条件,目的是保证数据的一致性。
4 数据库结构
● RDBMS通常使用客户端/服务器这样的系统结构。
● 通过从客户端向服务器端发送SQL语句来实现数据库的读写操作。
● 关系数据库采用被称为数据库表的二维表来管理数据。
● 数据库表由表示数据项目的列(字段)和表示一条数据的行(记录)所组
成,以记录为单位进行数据读写。
● 本书将行和列交汇的方格称为单元格,每个单元格只能输入一个数据。
客户端/服务器类型结构:
数据库和表的关系:根据 SQL 语句的内容返回的数据同样必须是二维表的形式 ,这也是关
系数据库的特征之一。返回结果如果不是二维表的 SQL 语句则无法执行。
表的列(垂直方向)称为字段,它代表了保存在表中的数据项目。表的行(水平方向)称为记录,它相当于一条数据。 关系数据库必须以行为单位进行数据读写。行和列交汇的方格称为单元格。 一个单元格中只能输入一个数据 。
4 SQL概要
总览:
● SQL是为操作数据库而开发的语言。
● 虽然SQL也有标准,但实际上根据RDBMS的不同SQL也不尽相同。
● SQL通过一条语句来描述想要进行的操作,发送给RDBMS。
● 原则上SQL语句都会使用分号结尾。
● SQL根据操作目的可以分为DDL、DML和DCL。
SQL分类:
学会标准SQL就可以在各种RDBMS中书写SQL语句了。
SQL 用关键字、表名、列名等组合而成的一条语句(SQL 语句)来描述操作的内容。
SQL可以分为三类:DDL(Data Definition Language,数据定义语言) 用来创建或者删除存储数据用的数据库以及数据库中的表等对象。DDL 包含以下几种指令。
CREATE : 创建数据库和表等对象
DROP : 删除数据库和表等对象
ALTER : 修改数据库和表等对象的结构
DML(Data Manipulation Language,数据操纵语言) 用来查询或者变更表中的记录。DML 包含以下几种指令。
SELECT :查询表中的数据
INSERT :向表中插入新数据
UPDATE :更新表中的数据
DELETE :删除表中的数据
DCL(Data Control Language,数据控制语言) 用来确认或者取消对数据库中的数据进行的变更。除此之外,还可以对 RDBMS 的用户是否有权限
操作数据库中的对象(数据库表等)进行设定。DCL 包含以下几种指令。
COMMIT : 确认对数据库中的数据进行的变更
ROLLBACK : 取消对数据库中的数据进行的变更
GRANT : 赋予用户操作权限
REVOKE : 取消用户的操作权限
其中,实际使用的最多是DML
基本书写规则:SQL语句以分号( ; )结尾。SQL 不区分关键字的大小写 。但是插入到表中的数据是区分大小写的。
在 SQL 语句中直接书写的字符串、日期或者数字等称为常数。常数有其对应的书写方式: ' abc ' '2010-01-26',即字符串和日期常数需要使用单引号(')括起来。数字常数无需加注单引号(直接书写数字即可)。
SQL 语句的单词之间需使用半角空格或换行符来进行分隔。
5 表的创建
总览:
● 表通过 CREATE TABLE 语句创建而成。
● 表和列的命名要使用有意义的文字。
● 指定列的数据类型(整数型、字符型和日期型等)。
● 可以在表中设置约束(主键约束和 NOT NULL 约束等)。
表的内容创建:
创建数据库 CREATE DATABASE < 数据库名称 > ;
创建表:
命名规则:
我们只能使用半角英文字母、数字、下划线(_)作为数据库、表和列的名称 。此外,名称必须以半角英文字母开头 。最后还有一点,在同一个数据库中不能创建两个相同名称的表,在同一个表中也不能创建两个名称相同的列。
数据类型的指定:
所有的列都必须指定数据类型。
INTEGER型 用来指定存储整数的列的数据类型(数字型)不能存储小数。
CHAR 型 CHAR 是 CHARACTER(字符)的缩写,是用来指定存储字符串的列的数据类型(字符型)。字符串以定长字符串 的形式存储在被指定为 CHAR 型的列中。
VARCHAR 型也是用来指定存储字符串的列的数据类型(字符串类型),也可以通过括号内的数字来指定字符串的长度(最大长度)。但该类型的列是以 可变长字符串 的形式来保存字符串的 。
DATE 型用来指定存储日期(年月日)的列的数据类型(日期型)。
约束的设置:
数据类型的右侧设置了 NOT NULL 约束。 NULL 是代表空白(无记录)的关键字A 。在NULL 之前加上了表示否定的 NOT,就是给该列设置了不能输入空白
是用来给 product_ id 列设置主键约束。所谓键,就是在指定特定数据时使用的列的组合。键种类多样,主键(primary key)就是可以特定一行数据的列。也就是说,如果把product _ id 列指定为主键,就可以通过该列取出特定的商品数据了。
6 表的删除和更新
总览:
● 使用 DROP TABLE 语句来删除表。
● 使用 ALTER TABLE 语句向表中添加列或者从表中删除列。
删除表:
删除了的表是无法恢复的。
在执行 DROP TABLE 语句之前请务必仔细确认。
添加列:
删除列:
表定义变更之后无法恢复。在执行 ALTER TABLE 语句之前请务必仔细确认。
插入数据:
使用插入行的指令语句 INSERT ,就可以把表 1-2 中的数据都插入到表中了。开头的 BEGIN TRANSACTION 语句是开始插入行的指令语句,结尾的 COMMIT 语句是确定插入行的指令语句。
二 查询基础
SELECT 语句是 SQL 最基本也是最重要的语句。
1 SELECT 语句基础
总览:
● 使用 SELECT 语句从表中选取数据。
● 为列设定显示用的别名。
● SELECT 语句中可以使用常数或者表达式。
● 通过指定 DISTINCT 可以删除重复的行。
● SQL语句中可以使用注释。
● 可以通过 WHERE 语句从表中选取出符合查询条件的数据。
通过 SELECT 语句查询并选取出必要数据的过程称为匹配查询或查询(query)。
基本语法:
查询结果中列的顺序和SELECT 子句中的顺序相同
星号( * )代表全部列的意思。
SQL 语句可以使用 AS 关键字为列设定别名
别名可以使用中文,使用中文时需要用双引号(")括起来。
常数查询:
删除重复行:
DISTINCT 关键字只能用在第一个列名之前
WHERE语句:
SELECT 语句通过 WHERE 子句来指定查询数据的条件。在 WHERE子句中可以指定“某一列的值和这个字符串相等”或者“某一列的值大于这个数字”等条件。执行含有这些条件的 SELECT 语句,就可以查询出只符合该条件的记录了
WHERE 子句要紧跟在 FROM 子句之后。
注释:
2 算术运算符与比较运算符
总览:
● 运算符就是对其两边的列或者值进行运算(计算或者比较大小等)的符号。
● 使用算术运算符可以进行四则运算。
● 括号可以提升运算的优先顺序(优先进行运算)。
● 包含 NULL 的运算,其结果也是 NULL 。
● 比较运算符可以用来判断列或者值是否相等,还可以用来比较大小。
● 判断是否为 NULL ,需要使用 IS NULL 或者 IS NOT NULL 运算符。
斗鱼
运算就是这样以行为单位执行的。SQL 中也可以像平常的运算表达式那样使用括号 ( ) 。
所有包含 NULL 的计算,结果肯定是 NULL 。
比较运算符
一定要让不等号在左,等号在右。
字符串类型的数据原则上按照字典顺序进行排序,不能与数字的大小顺序混淆。
不能对 NULL 使用比较运算符,SQL提供了专门用来判断是否为 NULL 的 IS NULL 运算符。
3 逻辑运算符
总览:● 通过使用逻辑运算符,可以将多个查询条件进行组合。
● 通过 NOT 运算符可以生成“不是~”这样的查询条件。
● 两边条件都成立时,使用 AND 运算符的查询条件才成立。
● 只要两边的条件中有一个成立,使用 OR 运算符的查询条件就可以成立。
● 值可以归结为真( TRUE )和假( FALSE )其中之一的值称为真值。比较运
算符在比较成立时返回真,不成立时返回假。但是,在SQL中还存在另外
一个特定的真值——不确定(UNKNOWN)。
● 将根据逻辑运算符对真值进行的操作及其结果汇总成的表称为真值表。
● SQL中的逻辑运算是包含对真、假和不确定进行运算的三值逻辑。
NOT 运算符用来否定某一条件,但是不能滥用。AND 运算符在其两侧的查询条件都成立时整个查询条件才成立。OR 运算符在其两侧的查询条件有一个成立时整个查询条件都成立。
文式图很方便:
AND 运算符的优先级高于 OR 运算符。想要优先执行 OR 运算符时可以使用括号。
与通常的逻辑运算被称为二值逻辑相对,只有 SQL 中的逻辑运算被称为三值逻辑。
三 聚合与排序
1 对表进行聚合排序
总览:● 使用聚合函数对表中的列进行计算合计值或者平均值等的汇总操作。
● 通常,聚合函数会对 NULL 以外的对象进行汇总。但是只有 COUNT 函数
例外,使用 COUNT (*)可以查出包含 NULL 在内的全部数据的行数。
● 使用 DISTINCT 关键字删除重复值。
以下 5 个常用的函数。
COUNT : 计算表中的记录数(行数)
SUM : 计算表中数值列中数据的合计值
AVG : 计算表中数值列中数据的平均值
MAX : 求出表中任意列中数据的最大值
MIN : 求出表中任意列中数据的最小值
如上所示,用于汇总的函数称为聚合函数或者聚集函数,本书中统称为聚合函数。所谓聚合,就是将多行汇总为一行。
2 对表进行分组
总览:
使用 GROUP BY 子句可以像切蛋糕那样将表分割。通过使用聚合函数和
GROUP BY 子句,可以根据“商品种类”或者“登记日期”等将表分割后再
进行汇总。
● 聚合键中包含 NULL 时,在结果中会以“不确定”行(空行)的形式表现出来。
● 使用聚合函数和 GROUP BY 子句时需要注意以下4点。
① 只能写在 SELECT 子句之中
② GROUP BY 子句中不能使用 SELECT 子句中列的别名
③ GROUP BY 子句的聚合结果是无序的
④ WHERE 子句中不能使用聚合函数
GROUP BY 就像是切分表的一把刀。一定要写在FROM 语句之后(如果有 WHERE 子句的话需要写在 WHERE 子句之后)。
聚合键中包含 NULL 时,在结果中会以“不确定”行(空行)的形式表现出来。
常见错误:
■常见错误① ——在 SELECT 子句中书写了多余的列
■常见错误② ——在 GROUP BY 子句中写了列的别名
■常见错误③ —— GROUP BY 子句的结果能排序吗
GROUP BY 子句结果的显示是无序的
■常见错误④ ——在 WHERE 子句中使用聚合函数
只有 SELECT 子句和 HAVING 子句(以及 ORDER BY 子句)中能够使用聚合函数。
3 为聚合结果指定条件
● 使用 COUNT 函数等对表中数据进行汇总操作时,为其指定条件的不是
WHERE 子句,而是 HAVING 子句。
● 聚合函数可以在 SELECT 子句、 HAVING 子句和 ORDER BY 子句中使用。
● HAVING 子句要写在 GROUP BY 子句之后。
● WHERE 子句用来指定数据行的条件, HAVING 子句用来指定分组的条件。
HAVING 子句要写在 GROUP BY 子句之后。
HAVING 子句中能够使用的 3 种要素如下所示。
● 常数
● 聚合函数
● GROUP BY 子句中指定的列名(即聚合键)
有些条件既可以写在 HAVING 子句当中,又可以写在 WHERE 子句当中。这些条件就是聚合键所对应的条件
聚合键所对应的条件不应该书写在 HAVING 子句当中,而应该书写在 WHERE 子句当中。
4 对查询结果进行排序
● 使用 ORDER BY 子句对查询结果进行排序。
● 在 ORDER BY 子句中列名的后面使用关键字 ASC 可以进行升序排序,使
用 DESC 关键字可以进行降序排序。
● ORDER BY 子句中可以指定多个排序键。
● 排序健中包含 NULL 时,会在开头或末尾进行汇总。
● ORDER BY 子句中可以使用 SELECT 子句中定义的列的别名。
● ORDER BY 子句中可以使用 SELECT 子句中未出现的列或者聚合函数。
● ORDER BY 子句中不能使用列的编号。
ORDER BY 子句通常写在 SELECT 语句的末尾。
降序:在列名后面使用 DESC 关键字。未指定 ORDER BY 子句中排列顺序时会默认使用升序进行排列。
使用含有 NULL 的列作为排序键时,NULL 会在结果的开头或末尾汇总显示
在 ORDER BY 子句中可以使用 SELECT 子句中定义的别名。要记住 SELECT 子句的执行顺序在 GROUP BY 子句之后, ORDER BY 子句之前。
在 ORDER BY 子句中可以使用 SELECT 子句中未使用的列和聚合函数。
不建议列编号:代码阅读起来比较难。该排序功能将来会被删除。
四 数据更新
1 插入
● 使用 INSERT 语句可以向表中插入数据(行)。原则上, INSERT 语句每
次执行一行数据的插入。
● 将列名和值用逗号隔开,分别括在()内,这种形式称为清单。
● 对表中所有列进行 INSERT 操作时可以省略表名后的列清单。
● 插入 NULL 时需要在 VALUES 子句的值清单中写入 NULL 。
● 可以为表中的列设定默认值(初始值),默认值可以通过在 CREATE TABLE
语句中为列设置 DEFAULT 约束来设定。
● 插入默认值可以通过两种方式实现,即在 INSERT 语句的 VALUES 子句
中指定 DEFAULT 关键字(显式方法),或省略列清单(隐式方法)。
● 使用 INSERT … SELECT 可以从其他表中复制数据。
将列名和值用逗号隔开,分别括在 () 内,这种形式称为清单。原则上,执行一次 INSERT 语句会插入一行数据。
对表进行全列 INSERT 时,可以省略表名后的列清单。
INSERT 语句中想给某一列赋予 NULL 值时,可以直接在 VALUES子句的值清单中写入 NULL 。
可以通过在创建表的CREATE TABLE 语句中设置 DEFAULT 约束来设定默认值。
■通过显式方法插入默认值(推荐)
在 VALUES 子句中指定 DEFAULT 关键字
■通过隐式方法插入默认值
插入默认值时也可以不使用 DEFAULT 关键字,只要在列清单和VALUES 中省略设定了默认值的列就可以了。
省略 INSERT 语句中的列名,就会自动设定为该列的默认值(没有默认值时会设定为 NULL )。
复制表
INSERT 语句的 SELECT 语句中,可以使用 WHERE 子句或者 GROUP BY 子句等任何SQL语法 (但使用 ORDER BY 子句并不会产生任何效果)。
2 数据的删除( DELETE 语句的使用方法)
● 如果想将整个表全部删除,可以使用 DROP TABLE 语句,如果只想删除表中全部数据,需使用 DELETE 语句。
● 如果想删除部分数据行,只需在 WHERE 子句中书写对象数据的条件即可。通过 WHERE 子句指定删除对象的 DELETE 语句称为搜索型 DELETE 语句。
① DROP TABLE 语句可以将表完全删除
② DELETE 语句会留下表(容器),而删除表中的全部数据
如果语句中忘了写 FROM ,而是写成了“ DELETE < 表名 >”,或者写了多余的列名,都会出错,无法正常执行,请大家特别注意。无法正常执行的原因是删除对象不是表,而是表中的数据行(记录)。DELETE 语句的对象是行而不是列,所以 DELETE 语句无法只删除部分列的数据。
可以像 SELECT 语句那样使用 WHERE子句指定删除条件。这种指定了删除对象的 DELETE 语句称为搜索型DELETE
3 数据的更新( UPDATE 语句的使用方法)
● 使用 UPDATE 语句可以更改(更新)表中的数据。
● 更新部分数据行时可以使用 WHERE 来指定更新对象的条件。通过 WHERE子句指定更新对象的 UPDATE 语句称为搜索型 UPDATE 语句。
● UPDATE 语句可以将列的值更新为 NULL 。
● 同时更新多列时,可以在 UPDATE 语句的 SET 子句中,使用逗号分隔更新对象的多个列。
更新数据时也可以像DELETE 语句那样使用 WHERE 子句,这种指定更新对象的 UPDATE 语句称为搜索型 UPDATE 语句。
使用 UPDATE 语句可以将值清空为 NULL (但只限于未设置 NOT NULL 约束的列)。
4 事务
● 事务是需要在同一个处理单元中执行的一系列更新处理的集合。通过使用事务,可以对数据库中的数据更新处理的提交和取消进行管理。
● 事务处理的终止指令包括 COMMIT (提交处理)和 ROLLBACK (取消处理)两种。
● DBMS的事务具有原子性(Atomicity)、一致性(Consistency)、隔离性(Isolation)和持久性(Durability)四种特性。通常将这四种特性的首字母结合起来,统称为ACID特性。
事务就是 需要在同一个处理单元中执行的一系列更新处理的集合 。
■ COMMIT ——提交处理
COMMIT 是提交事务包含的全部更新处理的结束指令,相当于文件处理中的覆盖保存。一旦提交,就无法恢复到事务开始前的状态。
■ ROLLBACK ——取消处理
ROLLBACK 是取消事务包含的全部更新处理的结束指令,相当于文件处理中的放弃保存。
ACID 特性:所有 DBMS 都必须遵守的规则。
■原子性(Atomicity)
原子性是指在事务结束时,其中所包含的更新处理要么全部执行,要么完全不执行,也就是要么占有一切要么一无所有。
■一致性(Consistency)
一致性指的是事务中包含的处理要满足数据库提前设置的约束,如主键约束或者 NOT NULL 约束等。一致性也称为完整性。
■隔离性(Isolation)
隔离性指的是保证不同事务之间互不干扰的特性。
■持久性(Durability)
持久性也可以称为耐久性,指的是在事务(不论是提交还是回滚)结束后,DBMS 能够保证该时间点的数据状态会被保存的特性。
五 复杂查询
1 视图
● 从SQL的角度来看,视图和表是相同的,两者的区别在于表中保存的是实际的数据,而视图中保存的是 SELECT 语句(视图本身并不存储数据)。
● 使用视图,可以轻松完成跨多表查询数据等复杂操作。
● 可以将常用的 SELECT 语句做成视图来使用。
● 创建视图需要使用 CREATE VIEW 语句。
● 视图包含“不能使用 ORDER BY ”和“可对其进行有限制的更新”两项限制。
● 删除视图需要使用 DROP VIEW 语句。
视图和表到底有什么不同呢?区别只有一个,那就是“是否保存了实际的数据”。使用视图时并不会将数据保存到存储设备之中,而且也不会将数据保存到其他任何地方。实际上视图保存的是 SELECT 语句。表中存储的是实际数据,而视图中保存的是从表中取出数据所使用的 SELECT 语句。
视图的优点大体有两点。
第一点是由于视图无需保存数据,因此可以节省存储设备的容量。第二个优点就是可以将频繁使用的 SELECT 语句保存成视图,这样就不用每次都重新书写了。
创建视图需要使用 CREATE VIEW 语句:
视图就是保存好的 SELECT 语句。
使用视图的查询通常需要执行 2 条以上的 SELECT 语句。这里没有使用“2条”而使用了“2条以上”,是因为还可能出现以视图为
基础创建视图的多重视图。尽量避免在视图的基础上创建视图。这是因为对多数DBMS来说,多重视图会降低SQL的性能。
使用视图的限制:
视图的限制① ——定义视图时不能使用 ORDER BY 子句
视图的限制② ——对视图进行更新,视图和表需要同时进行更新,因此通过汇总得到的视图无法进行更新。
删除视图需要使用 DROP VIEW 语句:
2 子查询
● 一言以蔽之,子查询就是一次性视图( SELECT 语句)。与视图不同,子查
询在 SELECT 语句执行完毕之后就会消失。
● 由于子查询需要命名,因此需要根据处理内容来指定恰当的名称。
● 标量子查询就是只能返回一行一列的子查询。
子查询就是将用来定义视图的 SELECT 语句直接用于 FROM 子句当中。
以下功能相同:
子查询作为内层查询会首先执行。尽量避免使用多层嵌套的子查询。
标量子查询就是返回单一值的子查询。
对于标量子查询,能够使用常数或者列名的地方,无论是 SELECT 子句、 GROUP BY 子句、 HAVING 子句,还是ORDER BY 子句,几乎所有的地方都可以使用。
使用标量子查询时的注意事项,那就是该子查询绝对不能返回多行结果。
3 关联子查询
● 关联子查询会在细分的组内进行比较时使用。
● 关联子查询和 GROUP BY 子句一样,也可以对表中的数据进行切分。
● 关联子查询的结合条件如果未出现在子查询之中就会发生错误。
这里起到关键作用的就是在子查询中添加的 WHERE 子句的条件。该条件的意思就是,在同一商品种类中对各商品的销售单价和平均单价进行比较。在细分的组内进行比较时,需要使用关联子查询。
关联子查询也是用来对集合进行切分的。结合条件一定要写在子查询中。
六 函数、谓词、 CASE 表达式
1 函数
● 根据用途,函数可以大致分为算术函数、字符串函数、日期函数、转换函数和聚合函数。
● 函数的种类很多,无需全都记住,只需要记住具有代表性的函数就可以了,其他的可以在使用时再进行查询。
函数大致可以分为以下几种。
● 算术函数(用来进行数值计算的函数)
● 字符串函数(用来进行字符串操作的函数)
● 日期函数(用来进行日期操作的函数)
● 转换函数(用来转换数据类型和值的函数)
● 聚合函数(用来进行数据聚合的函数)
选一些有代表性的:
注意 || 函数在 SQL Server 和 MySQL 中无法使用。SQL Server使用“+”运算符(函数)来连接字符串A。MySQL使用 CONCAT 函数来完成字符串的拼接。
UPPER 是大写转换函数。
日期函数:
转换函数:
2 谓词
● 谓词就是返回值为真值的函数。
● 掌握 LIKE 的三种使用方法(前方一致、中间一致、后方一致)。
● 需要注意 BETWEEN 包含三个参数。
● 想要取得 NULL 数据时必须使用 IS NULL 。
● 可以将子查询作为 IN 和 EXISTS 的参数。
对通常的函数来说,返回值有可能是数字、字符串或者日期等,但是谓词的返回值全都是真值( TRUE/FALSE/UNKNOWN )。这也是谓词和函数的最大区别。
LIKE 谓词——字符串的部分一致查询
不使用“ = ”来指定条件字符串,而以字符串中是否包含该条件(本例中是“包含 ddd ”)的规则为基础的查询称为模式匹配
BETWEEN 谓词——范围查询,结果中会包含临界值
IS NULL 、 IS NOT NULL ——判断是否为 NULL
IN 谓词—— OR 的简便用法
EXIST 谓词——① EXIST 的使用方法与之前的都不相同
② 语法理解起来比较困难
③ 实际上即使不使用 EXIST ,基本上也都可以使用 IN (或者 NOT IN )来代替
谓词的作用就是“判断是否存在满足某种条件的记录”。
EXIST 只需要在右侧书写 1 个参数,该参数通常都会是一个子查询。 EXIST 通常都会使用关联子查询作为参数
作为 EXIST 参数的子查询中经常会使用 SELECT * 。
3 CASE表达式
● CASE 表达式分为简单 CASE 表达式和搜索 CASE 表达式两种。搜索CASE 表达式包含简单 CASE 表达式的全部功能。
● 虽然 CASE 表达式中的 ELSE 子句可以省略,但为了让SQL语句更加容易理解,还是希望大家不要省略。
● CASE 表达式中的 END 不能省略。
● 使用 CASE 表达式能够将 SELECT 语句的结果进行组合。
● 虽然有些DBMS提供了各自特有的 CASE 表达式的简化函数,例如Oracle中的 DECODE 和MySQL中的 IF ,等等,但由于它们并非通用的函数,功能上也有些限制,因此有些场合无法使用。
CASE 表达式的语法分为简单 CASE 表达式和搜索 CASE 表达式两种
虽然 CASE 表达式中的 ELSE 子句可以省略,但还是希望大家不要省略。
CASE 表达式中的 END 不能省略。
七 集合运算
1 表的加减法
● 集合运算就是对满足同一规则的记录进行的加减等四则运算。
● 使用 UNION (并集)、 INTERSECT (交集)、 EXCEPT (差集)等集合运算符来进行集合运算。
● 集合运算符可以去除重复行。
● 如果希望集合运算符保留重复行,就需要使用 ALL 选项。
表的加法—— UNION
集合运算符会除去重复的记录。
集合运算的注意事项:
注意事项① ——作为运算对象的记录的列数必须相同
注意事项② ——作为运算对象的记录中列的类型必须一致
注意事项③ —— 可以使用任何 SELECT 语句,但 ORDER BY 子句只能在最后使用一次
包含重复行的集合运算—— ALL 选项
选取表中公共部分—— INTERSECT
INTERSECT 应用于两张表,选取出它们当中的公共记录。
记录的减法—— EXCEPT
2 联结
● 联结( JOIN )就是将其他表中的列添加过来,进行“添加列”的集合运算。UNION 是以行(纵向)为单位进行操作,而联结则是以列(横向)为单位
进行的。
● 联结大体上分为内联结和外联结两种。首先请大家牢牢掌握这两种联结的使用方法。
● 请大家一定要使用标准SQL的语法格式来写联结运算,对于那些过时的或者特定SQL中的写法,了解一下即可,不建议使用。
联结( JOIN )运算,简单来说,就是将其他表中的列添加过来,进行“添加列”的运算
内联结—— INNER JOIN
外联结—— OUTER JOIN
●外联结要点① ——选取出单张表中全部的信息
联结只能选取出同时存在于两张表中的数据,对于外联结来说,只要数据存在于某一张表当中,就能够读取出来
●外联结要点②——外联结还有一点非常重要,那就是要把哪张表作为主表。最终的结果中会包含主表内所有的数据。指定主表的关键字是 LEFT 和 RIGHT 。
多表联结
交叉联结—— CROSS JOIN
内联结是交叉联结的一部分,“内”也可以理解为“包含在交叉联结结果中的部分”。相反,外联结的“外”可以理解为“交叉联结结果
之外的部分”。
八 SQL高级处理
1 窗口函数
● 窗口函数可以进行排序、生成序列号等一般的聚合函数无法实现的高级
操作。
● 理解 PARTITION BY 和 ORDER BY 这两个关键字的含义十分重要。
窗口函数也称为 OLAP 函数。OLAP 是 OnLine Analytical Processing 的简称,意思是对数据库数据进行实时分析处理。
窗口函数大体可以分为以下两种。
① 能够作为窗口函数的聚合函数( SUM 、 AVG 、 COUNT 、 MAX 、 MIN )
② RANK 、 DENSE _ RANK 、 ROW _ NUMBER 等专用窗口函数
PARTITION BY 能够设定排序的对象范围。ORDER BY 能够指定按照哪一列、何种顺序进行排序。可以通过关键字ASC/DESC 来指定升序和降序。省略该关键字时会默认按照 ASC ,也就是升序进行排序。
窗口函数兼具分组和排序两种功能。
通过 PARTITION BY 分组后的记录集合称为“窗口”。不指定 PARTITION BY 和使用没有 GROUP BY 的聚合函数时的效果一样,也就是将整个表作为一个大的窗口来使用。
专用函数分类:
● RANK 函数
计算排序时,如果存在相同位次的记录,则会跳过之后的位次。
例)有 3 条记录排在第 1 位时:1 位、1 位、1 位、4 位……
● DENSE_RANK 函数
同样是计算排序,即使存在相同位次的记录,也不会跳过之后的位次。
例)有 3 条记录排在第 1 位时:1 位、1 位、1 位、2 位……
● ROW_NUMBER 函数
赋予唯一的连续位次。
例)有 3 条记录排在第 1 位时:1 位、2 位、3 位、4 位……
由于专用窗口函数无需参数,因此通常括号中都是空的。
窗口函数的适用范围:
原则上窗口函数只能在 SELECT 子句中使用。在 SELECT 子句之外“使用窗口函数是没有意义的”
窗口函数就是将表以窗口为单位进行分割,并在其中进行排序的函数。其实其中还包含在窗口中指定更加详细的汇总范围的备选功能,该备选功能中的汇总范围称为框架。
由于框架是根据当前记录来确定的,因此和固定的窗口不同,其范围会随着当前记录的变化而变化。这样的统计方法称为移动平均(moving average)。
将聚合函数作为窗口函数使用时,会以当前记录为基准来决定汇总对象的记录。
2 GROUPING 运算符
● 只使用 GROUP BY 子句和聚合函数是无法同时得出小计和合计的。如果想
要同时得到,可以使用 GROUPING 运算符。
● 理解 GROUPING 运算符中 CUBE 的关键在于形成“积木搭建出的立方体”的印象。
● 虽然 GROUPING 运算符是标准SQL的功能,但还是有些DBMS尚未支持这
一功能。
GROUPING 运算符包含以下 3 种。
● ROLLUP
● CUBE
● GROUPING SETS
超级分组记录默认使用 NULL 作为聚合键。
ROLLUP 是“卷起”的意思,比如卷起百叶窗、窗帘卷,等等。其名称也形象地说明了该操作能够得到像从小计到合计这样,从最小的聚合级开始,聚合单位逐渐扩大的结果。
SQL 提供了一个用来判断超级分组记录的 NULL 的特定函数 —— GROUPING 函数。该函数在其参数列的值为超级分组记录
所产生的 NULL 时返回 1 ,其他情况返回 0
使用 GROUPING 函数能够简单地分辨出原始数据中的 NULL 和超级分组记录中的 NULL 。
可以把 CUBE 理解为将使用聚合键进行切割的模块堆积成一个立方体。
GROUPING SETS 。该运算符可以用于从 ROLLUP 或者 CUBE 的结果中取出部分记录。
九 通过应用程序连接数据库
1 数据库世界和应用程序世界的连接
● 在实际的系统中是通过应用程序向数据库发送SQL语句的。
● 此时,需要通过“驱动”这座桥梁来连接应用程序世界和数据库世界。如果没有驱动,应用程序就无法连接数据库。
● 数据库和编程语言之间的驱动有很多种,如果不注意的话就会发生驱动不匹配的情况。
驱动就是一个用来连接应用和数据库的非常小的特殊程序(大概只有几百 KB)。在两者之间插入驱动程序之后,应用方面
就可以只针对应用进行特别处理,数据库方面也可以只针对数据库进行特别处理了。换言之,驱动就是应用和数据库这两个世界之间的桥梁。大家并不需要特意去编写驱动程序,通常情况下 DBMS 都会提供相应的驱动程序。
2 Java基础知识
● 执行Java 程序时,必须先对源代码进行编译。
● 与SQL语句不同,Java源代码的保留字是区分大小写的。
执行Java程序之前,必须对源代码进行编译。
Java源代码中的保留字要区分大小写,这是它和数据库的不同点之一。
Java源代码中不能出现全角字符/全角空格(注释除外)。
3 通过Java连接PostgreSQL
● 可以使用Java程序,通过驱动来执行各种各样的SQL语句。
● 通过数据库将 SELECT 语句的结果传递给Java程序之后,只能逐条循环访问。这就是可以同时操作多条数据的数据库世界和每次只能操作一条数据的程序世界的区别
在Java等程序语言的世界中,每次只能访问一条数据。因此,在访问多条数据时,需要使用循环处理。