关系模型概念
关系是对表的一种关系描述,关系里面元组不可重复但是表可以
关系中行的顺序,列的顺序可以调换
每个列的类型是一致的,要么是整形或者别的
第一范式
属性不可再分,叫做关系的第一范式

候选码(候选键)
关系模型中(Table表)某属性组可以区分或者标识元组。就是说哪个或者哪几个属性可以唯一的标识元组呢?
例如学生的关系靠学号,用姓名不行(重名),同理生日其他都不行
候选码可以有多个
主键
有多个候选码时选择一个作为主键
外键
关系 R 的一个属性组,它不是R的候选码但是它与另外一个关系 S 的候选码对应

关系模型操作
并运算
要满足并相容性,两个关系的域要相同,也就是说属性数目相同,属性类型和取值相同才可以做并集
运算结果需要去掉重复值
差运算
需要并相容性,表示出现在某一关系不在另一关系的集合
广义积运算

就是把所有可能的组合列出来
选择操作
选择某行
投影操作
从某种关系里选取某些列组成新的关系

theta连接操作
在两个关系的笛卡尔积里面选取某些特定关系的元组

连接操作很快尽量用
自然连接
从在两个关系R,S的笛卡尔积中选与另一个关系B里相同属性组,也就是笛卡尔积里面一定有某些元组和B一样的
是一种特殊的等值连接
SQL语言(1)
DDL数据定义语言,CREATE DTABASE
DML数据操纵语言, INSERT DELETE UPDATE SELECT等
sql是DDL,DML,DCL(数据控制语言)一体的语言
DDL:CREATE建立,ALTER修改,DROP撤销
DML:INSERT,DELETE,UPDATE,SELECT
DCL:GRANT, REVOKE
定义数据库
先建立数据库
CREATE DATABASE 数据库名
再建立表
CREATE TABLE 表名(
列名 列数据类型 [主键 | 候选键][not null],
...
)
数据类型
- char固定长字符串
- varchar可变长字符串
- int整
- real浮点数
- data日期
- ...
示例:定义学生表
CREATE TABLE Student(
SId char(8) not null,
Sname char(10),
Ssex char(2)
)
表中追加元组
需要用到DML语言
INSERT INTO 表名[
列名,
列名,
...
]
VALUES(
值,
值,
...
)
值和列需要对应
示例:追加学生表
INSERT INTO Student
VALUES('434210','张三','男')
值按照表默认顺序
简单查询
语法:
SELECT 列名...
FROM 表名...
WHERE 条件
示例:
检索所有学生信息
SELECT *
FROM Student
检索学生姓名和性别
SELETC Sname,Ssex
FROM Student
检索表中年龄小于等于19岁的学生的姓名和年龄
SELECT Sname,Sage
FROM Student
WHERE Sage<=19
结果排序
在后面加
ORDER BY 列名 [ASC | DESC]
模糊查询
- % 匹配0个或者多个字符
- _ 匹配单个字符
- \ 转义字符用于去掉特殊字符的含义
示例:检索所有姓张的学生
SELECT Sname
FROM Student😊
WHERE Sname LIKE '张%'
多表联合查询
通过连接运算完成
语法:
SELECT 若干列名
FROM 若干表名
WHERE 条件
示例:按照001号课的成绩高到底显示学生姓名
SELECT Sname
FROM Student,SC
WHERE Student.S_Id = SC.C_Id AND SC.C_Id = '001'
ORDER BY Score DESC
表名.属性名 来限定
表的重命名
SELECT 列名 AS 列别名
FROM 表明 AS 表别名
WHERE 条件
示例:求有薪水差额的任意两位教师
SELECT T1.Tname as Teacher1,T2.Tname as Teacher2
FROM Teacher T1,Teacher T2
WHERE T1.Salary > T1.Salary
这里将Teacher表命名成两个所以可以用别名进行select
示例:求既学过001的课又学过002课的同学
SELECT S_Id
FROM SC S1,SC S2
WHERE S1.S_Id = S2.S_Id AND S1.C_Id = '001' AND S2.C_Id = '002'
SC是Student Course
S1.S_Id = S2.S_Id表示学生名字一致,连接
S1.C_Id = '001' AND S2.C_Id = '002'表示学过的课程
这里定义了S1是学习001,S2是学习002的
SQL的增删改
将检索出来的信息加到表中
INSERT INTO St(Sname)
SELECT Sname FROM Student WHERE Sname LIKE '张%'
删除元组(一行),DELETE命令
语法:
DELETE FROM 表名
WHERE 条件
更改元组用update
UPDATE 表名
SET 列名 = 表达式
WHERE 条件
例子:将计算机系教师工资上调10%
UPDATE Teacher
SET Salary = Salary*1.1
WHERE D_Id in (SELECT D_Id FROM Dept WHERE Dname = '计算机')
D代表学院,D_Id表示系号,查询某一系的系号等于计算机
撤销表
DROP TABLE 表名
DELETE FROM是删除元组,DROP是包括了结构全删
SQL复杂查询
子查询
出现在WHERE中的SELECT的语句,其返回了一个集合
IN子查询语法:
表达式 [NOT] IN 子查询
例子:列出张三,王三的所有信息
SELECT *
FROM Student
WHERE Sname IN ("张三","王三")
例子:列出选修001课的同学
SELECT S_Id,Sname
FROM Student
WHERE S_Id IN (SELECT S_Id FROM SC WHERE C_Id = '001')
例子:列出选修001和002课的同学
SELECT S_Id
FROM SC
WHERE C_Id = '001' AND S_Id in (SELECT S_Id FROM SC WHERE C_Id = '002')
先选001的同学,AND后面是选002课的
例子:找出001课最高的同学们
SELECT S_Id
FROM SC
WHERE C_Id = '001' AND Score >= ALL (SELECT Score FROM SC WHERE C_Id = '001')
子查询返回所有同学的成绩,相当于比所有同学都高
EXISTS子查询
测试集合是否为空
语法:
[NOT] EXISTS (子查询)
示例:搜索选修赵三老师的同学姓名
SELECT DISTINCT Sname
FROM Student
WHERE EXISTS
(SELECT *
FROM SC,Course,Teacher
WHERE SC.C_Id = Course.C_Id AND SC.S_Id = Student.S_Id AND Course.T_Id = Teacher.T_Id AND Tname = '赵三')
Student和SC连接,SC和Course连接,Course和Teacher连接
聚集函数
就是表达式运算,不允许用在WHERE中
- COUNT 求个数
- SUM 求和
- AVG 求平均
- MAX 最大
- MIN 最小
例子:求计算机系教师工资总和
SELECT SUM(Salary)
FROM Teacher,Dept
WHERE Dept.Dname = '计算机' AND Dept.D_Id = Teacher.D_Id
分组
按照某条件分类
语法:
GROUP BY 分组条件
可以按照列进行分组

示例:求不及格课程超过两门的学生学号
SELECT S_Id FROM SC
WHERE Score<60
GROUP BY S_Id HAVING COUNT(*)>2
HAVING表示提取满足条件的分组