等值联接
多表查询语句中的连接条件使用的是等号,例:Student.Sno=SC.Sno
例:
Student
SC:
查询每个学生及其选修课程的情况
select Student.*,SC.* from Student,SC where Student.Sno=SC.Sno;
查询选修2号课程且成绩在88分以上的所有学生的学号和姓名
select Student.Sno,Sname from Student,SC where Student.Sno=SC.Sno and SC.Cno='2' and SC.Grade>'88';
对于”select Student.Sno,Sname“,Sno在两张表都出现了,所以必须加上表名或者别名前缀,Sname只在Student表中出现,引用时可以去掉。
等值连接和自然连接的区别:
1.自然连接一定是等值连接,但等值连接不一定是自然连接。
例如在数据库中:
S:
R:
等值连接(S.A=R.C)
等值连接(S.B=R.B)
自然连接
2.等值连接要求相等的分量,不一定是公共属性;而自然连接要求相等的分量必须是公共属性。
3.等值连接不把重复的属性除去;而自然连接要把重复的属性除去。所以等值连接将目标列重复的属性列去掉,就是自然连接
注:
两个关系R和S在做自然联接时,关系R中某些元组有可能在S中不存在公共属性上值相等的元组,从而造成R中这些元组(悬挂元组)在操作时被舍弃了,这些被舍弃的元组称为悬浮元组,又称为悬挂元组。
例如:S中的5,9 R中的7,2
补充:
半连接:关系R和S的半连接是R和S的自然连接在关系R的属性集上的投影
关系R
关系S
非等值联接:多表查询语句中的连接条件不是使用等号
例如:下面的between..and...,就表示员工表(emp)中员工的工资,不能超过职级表(jg)中的最高工资,不能低于其最低工资。
SELECT emp.employee_id, emp.last_name, jg.grade_level
FROM employees emp, job_grades jg
WHERE emp.salary BETWEEN jg.lowest_sal AND jg.highest_sal;
自身连接(自连接)
一个表与其自己进行连接,由于属性名都是同名属性,因此需要给表起别名前缀
SPJ表:
检索至少使用了零件编号为P3,P5的工程编号JNO
法一:使用where
select distinct X.JNO from SPJ AS X,SPJ AS Y WHERE X.JNO=Y.JNO AND X.PNO='P3' AND Y.PNO='P5';
法二:使用 inner join ....on(也可以使用join.....on)
select distinct X.JNO from SPJ X inner join SPJ Y on X.JNO=Y.JNO where X.PNO='P3' and Y.PNO='P5';
外连接:(left/right/full)outer join...on
还是用开头的例子:
Student:
SC:
left outer join....on
左外连接,LEFT OUTER JOIN,告诉DBMS生成的结果表中,除了包括匹配行外,还包括JOIN关键字(FROM子句中)左边表的不匹配行,即将左边表的悬浮元组保存在结果关系中,而其他属性填上空值。左外连接实际上可以表示为:
左外连接 = 内连接 + 左边表中失配的元组
select Student.Sno,Sname,Ssex,Sage,Sdept,Cno,Grade from Student LEFT OUTER JOIN SC ON (Student.Sno=SC.Sno);
right outer join..on
右外连接(RIGHT OUTER JOIN)告诉DBMS生成的结果表中,除了包括匹配行外,还包括JOIN关键字(FROM子句中)右边表的不匹配行,即将右边表中的悬浮元组保留下来,而在其他属性上填入空值。右外连接实际上可以表示为:
右外连接 = 内连接 + 右边表中失配的元组
full outer join..on
全外连接,FULL OUTER JOIN,告诉DBMS生成的结果表中,除了包括匹配行外,还包括JOIN关键字(FROM子句中)左边表和右边表的不匹配行,即把两张表的悬浮元组都保留下来,其他属性填为空值。全外连接实际上可以表示为:
全外连接 = 内连接 + 左边表中失配的元组 + 右边表中失配的元组。
这个例子展现的关系不明显,在举一个例子:
关系R:
关系S:
左外连接:
右外连接:
全外连接:
外部并:
两个关系R和S在做并操作时,构成的新关系属性由R和S的所有属性组成(公共属性只取一次),新关系的元组由属于R或属于S的元组构成,同时元组在新增加的属性上填空值。
交叉连接CROSS JOIN
结果包含所有连接表中的所有可能的行组合,交叉连接返回的是两个表的笛卡尔积
例:
select Student.Sno,Sname,Ssex,Sage,Sdept,Cno,Grade from Student CROSS JOIN SC
将会返回所有可能的组合
如果加上“where (Student.Sno=SC.Sno);”
select Student.Sno,Sname,Ssex,Sage,Sdept,Cno,Grade
from Student cross JOIN SC
where (Student.Sno=SC.Sno);
结果:
我们发现,将cross join换成“,”(逗号)效果相同