Note02- 结构化查询语言 SQL

SQL 语言有以下几个部分:

数据定义

SQL 的 DDL 包括以下语句:

创建 删除 修改
CREATE TABLE DROP TABLE ALTER TABLE
视图 CREATE VIEW DROP VIEW
索引 CREATE INDEX DROP INDEX

CREATE TABLE

例:

CREATE TABLE Student
	(SSN CHAR(9) NOT NULL,
	 Name VARCHAR(15) NOT NULL,
	 Year INTEGER,
	 Specialty VARCHAR(30),
	 Department VARCHAR(30),
	 Primary key (SSN));

CREATE TABLE Grade
    ( SSN CHAR(9) NOT NULL,
     CNO CHAR(7) NOT NULL,
     Score INTEGER,
     Primary key (SSN, CNO),
     foreign key(SSN) references Student
     foreign key(CNO) references Course); 

ALTER TABLE

CREATE INDEX

建立索引有什么用呢?

比如有如下 TABLE:

我想要找到所有 CS/MA 系的学生,可以用如下语句:

Select *
From student
Where sdept in ('MA', 'CS')

数据库系统可能会使用顺序扫描,逐元组查询的方式,为 O(n) 的时间复杂度。而如果在 Sdept 属性上建立了索引,那么时间复杂度就为 O(1)

CREATE VIEW

建立计算机系学生的视图:

CREATE VIEW CS_Student
	AS
	SELECT Sno, Sname, Sage
	FROM Student
	WHERE Sdept= 'CS';

查询

单表查询

查询仅涉及一个表,是一种最简单的查询操作,包括:

:::caution 注意

任何没出现在 Group by 子句中的属性如果出现在 Select 子句中,它只能出现在聚集函数内部。如下写法就是错的:

select dept_name, ID, avg(salary)
from instructor
group by dept_name

:::

连接查询

同时涉及多个表的查询称为连接查询。例:

查询选修 2 号课且成绩 90 分以上学生姓名

Select sname
From student, sc
Where student.sno=sc.sno and
cno='2' and grade>90;

查询每个学生的学号、姓名、选修的课程名及成绩

Select student.sno, sname, cname, grade
From student, sc, course
Where student.sno=sc.sno and
sc.cno=course.cno;

嵌套子查询

一个 SELECT-FROM-WHERE 语句称为一个查询块,将一个查询块嵌套在另一个查询块的 WHERE 子句、FROM 子句、或 HAVING 短语的条件中的查询称为嵌套子查询

例:

查询选修了 1 号课的学生姓名

Select sname
From student as S
Where exists (
			  Select *
			  From sc
			  where sno=S.sno and cno='1'
);

查询系平均工资超过 42000 美元的那些系名与教师平均工资

Select dept_name, avg_salary
From ( 
      Select dept_name, Avg(salary) as avg_salary
      From instuctor
      Group by dept_name
)
Where avg_salary>42000;

集合查询

参加集合操作的各结果表列数必须相同; 对应的数据类型也必须相同,系统自动去掉重复行

例:

查询 CS 系或年龄不大于 19 岁的学生

(Select *
From student
Where sdept='CS' )
UNION
(Select *
From student
Where sage<=19);

查询 CS 系的年龄不大于 19 岁的学生

(Select *
From student
Where sdept='CS' )
INTERSECT
(Select *
From student
Where sage<=19);

查询 CS 系中年龄不小于 19 岁的学生

(Select *
From student
Where sdept='CS')
EXCEPT
(Select *
From student
Where sage<19);

数据更新

插入

DBMS 在执行插入、修改及删除语句时会检查所插入、修改、删除的元组是否破坏表上已定义的完整性规则

例,对每一个系,求学生的平均年龄,并把结果存入数据库

# 建表
CREATE TABLE Deptage
    (Sdept CHAR(15);
    Avgage SMALLINT);
# 插入数据
INSERT
INTO Deptage(Sdept,Avgage)
    SELECT Sdept,AVG(Sage)
    FROM Student
    GROUP BY Sdept;

修改

UPDATE <表名>
SET <列名>=<表达式>[,<列名>=<表达式>]...
[WHERE <条件>];

删除

DELETE
FROM <表名>
[WHERE <条件>];

事务

事务 (transaction) 由查询和更新语句的序列组成

触发器

触发器 (trigger) 是一条语句,当对数据修改时它自动被执行,设置触发器机制,必须满足两个要求:

一旦把一个触发器输入数据库,只要指定的事件发生,相应条件满足,数据库系统就有责任执行它

例:

使用触发器表示 SC 表参照 Course 表的完整性

create trigger check1 after insert on SC
    referencing new row as nrow
    for each row
    when (nrow.cno not in (
          select cno
          from course) )
    begin
    	rollback;
    end

create trigger check2 after delete on Course
    referencing old row as orow
    for each row
    when (orow.cno not in (select cno from Course)
    	  and orow.cno in (select cno from SC))
    begin
    	rollback;
    end

授权机制