首页 > 数据库 > Oracle > [转载]数据库的查询与视图(上)
第4章 数据库的查询和视图
4.1.1 选择列
通过SELECT语句的项组成结果表的列。
::=
SELECT [ ALL |DISTINCT ] [ TOP n [ PERCENT ] [ WITH TIES ] ]
{ *
| { table_name |view_name | table_alias } .*
| { colume_name |expression | IDENTITYCOL | ROWGUIDCOL }
[ [ AS ]column_alias ]
| column_alias =expression
} [ , … n ]
1. 选择一个表中指定的列
一般情况下,希望包含在结果表中的列表清单在SELECT关键字之后,就像前面用到的那样,当在SELECT关键字后面指定*时,就表示全部列都包含在结果表中。不指定*,可以列出一个表中的某些列,各列名之间要以逗号分隔。
4.1.1 选择列
【例4.1】查询XSCJ数据库的XS表中各个同学的姓名、专业名和总学分。
USE XSCJ
SELECT 姓名,专业名,总学分
FROM XS
4.1.1 选择列
【例4.2】查询XS表中计算机专业同学的学号、姓名和总学分。查询XS表中的所有列。
SELECT 学号,姓名,总学分
FROM XS
WHERE 专业名= ‘计算机’
GO
SELECT *
FROM XS
GO
当在SELECT语句指定列的位置上使用*号时,表示选择表的所有列。
执行后将列出XS表中的所有数据,如图4.2所示:
4.1.1 选择列
2. 修改查询结果中的列标题
当希望查询结果中的某些列或所有列显示时使用自己选择的列标题时,可以在列名之后使用AS子句来更改查询结果的列标题名。其中column_alias是指定的列标题。
【例4.3】查询XS表中计算机系同学的学号、姓名和总学分,结果中各列的标题 分别指定为number、name和mark。
SELECT 学号 AS number, 姓名 AS name,总学分 AS mark
FROM XS
WHERE 专业名= ‘计算机’
该语句的执行结果如图4.3所示。
更改查询结果中的列标题也可以使用column_alias=expression的形式。例如:
SELECT number = 学号, name = 姓名, mark = 总学分
FROM XS
WHERE 专业名= ’计算机’
该语句的执行结果与上例的结果完全相同。
4.1.1 选择列
注意,当自定义的列标题中含有空格时,必须使用引号将标题括起来。例如:
SELECT ‘Student number’ = 学号,姓名 AS ‘Student name’, mark = 总学分
FROM XS
WHERE 专业名= ‘计算机’
4.1.1 选择列
3. 替换查询结果中的数据
在对表进行查询时,有时对所查询的某些列希望得到的是一种概念而不是具体的数据。例如查询XS表的总学分,所希望知道的是学习的总体情况,这时,就可以用等级来替换总学分的具体数字。
要替换查询结果中的数据,则要使用查询中的CASE表达式,格式为:
CASE
WHEN 条件1 THEN 表达式1
WHEN 条件2 THEN 表达式2
……
ELSE 表达式
END
SQL Server按照顺序计算每一个条件,如果找到条件为真的语句,SQL Server就执行TEHN关键字后的表达式;否则执行可选的ELSE关键字后的语句。若没有为真的条件,也没有关键字,则CASE表达式返回值为空。
4.1.1 选择列
【例4.4】查询XS表中计算机系各同学的学号、姓名和总学分,对其总学分按以下规则进行替换:若总学分为空值,替换为“尚未选课”;若总学分小于50,替换为“不及格”;若总学分在50与52之间,替换为“合格”;若总学分大于52,替换为“优秀”。列标题更改为“等级”。
SELECT 学号, 姓名,
等级=
CASE
WHEN 总学分 IS NULL THEN ‘尚未选课’
WHEN 总学分 < 50 THEN ‘不及格’
WHEN 总学分 >=50 and 总学分<=52THEN ‘合格’
ELSE ‘优秀’
END
FROM XS
WHERE 专业名=’计算机’
4.1.1 选择列
4. 计算列值
使用SELECT对列进行查询时,在结果中可以输出对列值计算后的值,即SELECT子句可使用表达式作为结果,格式为:
SELECT expression[ , expression ]
【例4.5】按120分计算成绩显示。
SELECT 学号, 课程号,
成绩120=成绩*1.20
FROM XS_KC
4.1.1 选择列
计算列值使用算术运算符:+(加)、-(减)、*(乘)、/(除)和%(取余),其中5种算术运算符(+、-、*、/)可以用于任何数字类型的列,包括:int、smallint、tinyint、decimal、numeric、float、real、money和smallmoney;%可以用于上述除money和smallmoney以外的数字类型。
5. 消除结果集中的重复行
对表只选择其某些列时,可能会出现重复行。例如,若对XSCJ数据库的XS表只选择专业名和总学分,则出现多行重复的情况。可以使用DISTINCT关键字消除结果集中的重复行,其格式是:
SELECT DISTINCTcolumn_name [ , column_name…]
关键字DISTINCT的含义是对结果集中的重复行只选择一个,保证行的唯一性。
【例4.6】对XSCJ数据库的XS表只选择专业名和总学分,消除结果集中的重复行。
SELECT DISTINCT 专业名, 总学分
FROM XS
图4.6消除重复行
与DISTINCT相反,当使用关键字ALL时,将保留结果集的所有行。当SELECT语句中缺省ALL与DISTINCT时,默认值为ALL。
6. 限制结果集返回行数
如果SELECT语句返回的结果集的行数非常多,可以使用TOP选项限制其返回的行数。TOP选项的基本格式为:
TOP n [ PERCENT ]
其中n是一个正整数,表示返回查询结果集的前n行。若带PERCENT关键字,则表示返回结果集的前n%行。
4.1.1 选择列
【例4.7】对XSCJ数据库的XS表选择姓名、专业名和总学分,只返回结果集的前6行。
SELECT TOP 6 姓名,专业名,总学分
FROM XS
4.1.2 选择行
在SQL Server中,选择行是通过在SELECT语句中WHERE子句指定选择的条件来实现的。这一节将详细讨论WHERE子句中查询条件的构成。WHERE子句必须紧跟FROM子句之后,其基本格式为:
在SQL中,返回逻辑值(TRUE或FALSE)的运算符或关键字都可称为谓词。
1. 表达式比较
比较运算符用于比较两个表达式值,共有9个,分别是: =(等于)、<(小于)、<=(小于等于)、>(大于)、>=(大于等于)、<>(不等于)、!=(不等于)、!<(不小于)、!>(不大于)。比较运算的格式为:
expression { = |< | <= | > | >= | <> | != | !< | !> } expression
其中expression是除text、ntext和image外类型的表达式。
当两个表达式值均不为空值(NULL)时,比较运算返回逻辑值TRUE(真)或FALSE(假);而当两个表达式值中有一个为空值或都为空值时,比较运算将返回UNKNOWN。
【例4.8】查询XSCJ数据库XS表中通信工程专业总学分大于等于42的同学的情况。
SELECT *
FROM XS
WHERE专业名 = ‘通信工程’ and 总学分 >=42
4.1.2 选择行
2. 模式匹配
LIKE谓词用于指出一个字符串是否与指定的字符串相匹配,其运算对象可以是char、varchar、text、ntext、datetime和smalldatetime类型的数据,返回逻辑值TRUE或FALSE。LIKE谓词表达式的格式为:
string_expression[ NOT ] LIKE string_expression [ ESCAPE ‘escape_character’ ]
【例4.9】查询XSCJ数据库XS表中计算机系的学生情况。查询XSCJ数据库XS表中姓“王”且单名的学生情况。
SELECT *
FROM XS
WHERE 专业名 LIKE ‘计算机’
GO
SELECT *
FROM XS
WHERE 姓名 LIKE ‘王_’
GO
4.1.2 选择行
使用LIKE进行模式匹配时,常使用通配符,即可进行模糊查询。有关通配符的格式和含义请见附录中介绍T-SQL语言的相关说明。
执行结果如图4.8所示。
若要匹配的内容为通配符的字符(包括%、_、[] 、^),可使用关键字ESCAPE。以告诉系统其后的每个字符均作为实际匹配的字符,而不再作为通配符。
3. 范围比较
用于范围比较的关键字有两个:BETWEEN和IN。
当要查询的条件是某个值的范围时,可以使用BETWEEN关键字。BETWEEN关键字指出查询范围,格式为:
expression [ NOT ]BETWEEN expression1 AND expression2
4.1.2 选择行
当不使用NOT时,若表达式expression的值在表达式expression1与expression2之间(包括这两个值),则返回TRUE,否则返回FALSE;使用NOT时,返回值刚好相反。
注意:expression1的值不能大于expression2的值。
使用IN关键字可以指定一个值表,值表中列出所有可能的值,当与值表中的任一个匹配时,即返回TRUE,否则返回FALSE。使用IN关键字指定值表的格式为:
expression IN (expression [,…n])
【例4.10】查询XSCJ数据库XS表中不在1989年出生的学生情况。查询XSCJ数据库XS表中专业名为“计算机”或“通信工程”或“无线电”的学生的情况。
SELECT *
FROM XS
WHERE 出生时间 NOT BETWEEN ‘1989-1-1’ and ‘1989-12-31’
GO
SELECT *
FROM XS
WHERE 专业名 IN (’计算机’, ’通信工程’, ’无线电’)
GO
4.1.2 选择行
该语句与下列语句等价:
SELECT *
FROM XS
WHERE 专业名 = ’计算机’ or 专业名 = ’通信工程’ or 专业名 = ’无线电’
说明:IN关键字最主要的作用是表达子查询。
4. 空值比较
如果两个值当中有一个或者都为空,则对这两个值的比较结果是未知的。NULL谓词提供了一种方法,用来测试值为空或者非空。格式为:
expression IS [NOT ] NULL
当不使用NOT时,若表达式expression的值为空值,返回TRUE,否则返回FALSE;当使用NOT时,结果刚好相反。
【例4.11】查询XSCJ数据库中总学分尚不定的学生情况。
SELECT *
FROM XS
WHERE 总学分 IS NULL
4.1.2 选择行
5. CONTAINS谓词
若需要在表中搜索指定的单词、短语或近义词等,可以使用CONTAINS谓词。CONTAINS谓词用于在表中搜索指定的字符串,可以是精确匹配,也可以是模糊匹配,还可以是加权匹配。要使用CONTAINS谓词,必须在操作的表上事先建立全文索引。
CONTAINS ( {column | * } , ‘’)
上式中,column表示在指定的列中搜索,*表示在所有列中搜索; 为搜索的限定或说明。
::=
{ | | | | }
| {( ) { AND | AND NOT | OR } […n] }
说明:
simple_term:用于说明搜索的是单词还是短语,格式为:word | “phrase”,word为单词,即不含空格和标点符号的字符串;短语是含一个或多个空格的字符串。如果搜索的是短语,则需要用双引号将其括起来。
4.1.2 选择行
prefix_term:给出了要搜索的单词或短语必须匹配的前缀,格式为:
{ “word*” |“phase*”}
其中word为单词,phase为短语,当查询的串是是短语时,需用双引号定界。
generation_term:说明搜索包含原词的派生词,所谓派生词是指原词的名词单、复数形式或动词的各种时态等。格式为:
FORMSOF (INFLECTIONAL , [,…n])
proximity_term:表示搜索包含NEAR或~运算符左右两边的词或短语,格式为: { | } { { NEAR | ~ } { | }[…n]
weight_term:指明本语句是加权搜索,即查询的数据与给定的权重进行加权匹配,格式为:
ISABOUT ( { { | | | } [ WEUGHT (weight_value) ] } [,…n] )
其中weight_value是一个0~1之间的数,表示权重。
6. FREETEXT谓词
与CONTAINS谓词类似,FREETEXT谓词也用于在一个表中搜索单词或短语,并要求表已建全文索引。格式为:
FREETEXT ( {column | * }, ‘freetext_string’ )
其中freetext_string是要搜索的字符串。
FREETEXT的查询精度没有CONTAINS高,他并不要求对它们进行严格的模式匹配。 FREETEXT对所查询的串也没有写法要求,因此FREETEXT也称为自由式查询。
4.1.2 选择行
7. 子查询
子查询通常与IN、EXIST谓词及比较运算符结合使用。
(1)IN子查询
IN子查询用于进行一个给定值是否在子查询结果集中的判断,格式为:
expression [ NOT ]IN ( subquery )
其中subquery是子查询。当表达式expression与子查询subquery的结果表中的某个值相等时,IN谓词返回TRUE,否则返回FALSE;若使用了NOT,则返回的值刚好相反。
【例4.12】在XSCJ数据库中有描述课程情况的表KC和描述学生成绩表的表XS_KC,表的结构和样本数据见附录A。要查找选修了课程号为101的课程的学生的情况:
SELECT *
FROM XS
WHERE 学号 IN
( SELECT 学号 FROM XS_KC WHERE 课程号 = ‘101’ )
4.1.2 选择行
在执行包含子查询的SELECT语句时,系统先执行子查询,产生一个结果表,再执行查询。本例中,先执行子查询:
SELECT 学号
FROM XS_KC
WHERE 课程名 = ‘101’
SELECT *
FROM XS
WHERE 学号 NOT IN
( SELECT 学号
FROM XS_KC
WHERE 课程号 IN
( SELECT 课程号
FROM KC
WHERE 课程名 = '离散数学'
)
)
4.1.2 选择行
(2)比较子查询
这种子查询可以认为是IN子查询的扩展,它使表达式的值与子查询的结果进行比较运算,格式为:
expression { <| <= | = | > | >= | != | <> | !< | !> } { ALL | SOME | ANY} ( subquery )
其中expression为要进行比较的表达式,subquery是子查询。ALL、SOME和ANY说明对比较运算的限制。
ALL指定表达式要与子查询结果集中的每个值都进行比较,当表达式与每个值都满足比较的关系时,才返回TRUE,否则返回FALSE;
SOME或ANY表示表达式只要与子查询结果集中的某个值满足比较的关系时,就返回 TRUE,否则返回FALSE。
【例4.14】查找比所有计算机系的学生年龄都大的学生。
SELECT *
FROM XS
WHERE 出生时间
( SELECT 出生时间
FROM XS
WHERE 专业名 = '计算机'
)
【例4.15】查找课程号206的成绩不低于课程号101的最低成绩的学生的学号。
SELECT 学号
FROM XS_KC
WHERE 课程号 = '206' AND 成绩 !< ANY
( SELECT 成绩
FROM XS_KC
WHERE 课程号 = '101'
)
4.1.2 选择行
(3)EXISTS子查询
EXISTS谓词用于测试子查询的结果是否为空表,若子查询的结果集不为空,则EXISTS返回TRUE,否则返回FALSE。EXISTS还可与NOT结合使用,即NOT EXISTS,其返回值与EXIST刚好相反。格式为:
[ NOT ] EXISTS (subquery )
【例4.16】查找选修206号课程的学生姓名。
SELECT 姓名
FROM XS
WHERE EXISTS
( SELECT *
FROM XS_KC
WHERE 学号 = XS.学号 AND 课程号 = ‘206’
)
分析:
① 本例在子查询的条件中使用了限定形式的列名引用XS.学号,表示这里的学号列出自表XS。
4.1.2 选择行
② 本例与前面的子查询例子不同点是,前面的例子中,内层查询只处理一次,得到一个结果集,再依次处理外层查询;而本例的内层查询要处理多次,因为内层查询与XS.学号有关,外层查询中XS表的不同行有不同的学号值。这类子查询称为相关子查询,因为子查询的条件依赖与外层查询中的某些值。
【例4.17】查找选修了全部课程的同学的姓名。
SELECT 姓名
FROM XS
WHERE NOT EXISTS
(SELECT *
FROM KC
WHERE NOT EXISTS
( SELECT *
FROM XS_KC
WHERE 学号=XS.学号 AND 课程号=KC.课程号
)
)
4.1.3 FROM子句
SELECT的查询对象由FROM子句指定,其格式为:
[ FROM{} [,…n] ]
其中table_source指出了要查询的表或视图。
::=
table_name [ [ AS] table_alias ] [ WITH ( [,…] ) ]
| view_name [ [ AS] table_alias ]
| rowset_function[ [AS ] table_alias ]
| OPENXML
| derived_table [AS ] table_alias [ ( column_alias [,…n] ) ]
|
1. table_name
table_name指定SELECT语句要查询的表,从前面的例子中已经了解了其作用。可以使用AS选项为表指定别名,AS也可以省略,直接给出别名即可。别名主要用在相关子查询及连接查询中。
【例4.18】查找选修了学号为081102同学所选修的全部课程的同学的学号。
分析:本例即要查找这样的学号y,对所有的课程号x,若081102号同学选修了该课,那么y也选修了该课。
SELECT DISTINCT 学号
FROM XS_KC AS CJ1
WHERE NOT EXISTS
( SELECT *
FROM XS_KC AS CJ2
WHERE CJ2.学号 = ‘081102’ AND NOT EXISTS
( SELECT *
FROM XS_KC AS CJ3
WHERE CJ3.学号= CJ1.学号 AND CJ3.课程号 = CJ2.课程号
)
)
4.1.3 FROM子句
4.1.3 FROM子句
2. view_name
view_name为视图名,也可以为其指定别名。有关视图的介绍请见4.3节。
3. rowset_function
rowset_function是一个行集函数,行集函数通常返回一个表或视图。主要的行集函数有CONTAINSTABLE、FREETEXTTABLE、OPENDATASOURCE、OPENQUERY、OPENROWSET和OPENXML。
(1) CONTAINSTABLE函数
该函数与CONTAINS谓词相对应,用于对表进行全文查询,并且要求所查询的表上建立了全文索引。CONTAINSTABLE函数的语法格式为:
CONTAINSTABLE (table , { column | * } , ‘’ [ , top_n_by_rank] )
其中table是进行全文查询的表,column指定被查询的列,*指对所有列进行查询。 contains_search_condition与CONTAINS谓词中的搜索条件完全相同。
CONTAINSTABLE函数返回包含满足匹配条件的行,共有两列:KEY和RANK,其中KEY是包含被检索的字符串的行的主键值,RANK是一个等级值,指明行与字符串匹配的情况。可选项top_n_by_rank,说明只返回按RANK降序排列的结果表的前n行,其中n是正整数。
4.1.3 FROM子句
CONTAINSTABLE函数常与INNER JOIN结合使用。
(2) FREETEXTTABLE函数
FREETEXTTABLE函数与FREETEXT谓词相对应,它的使用与CONTAINSTABLE函数类似,格式为:
FREETEXTTABLE (table , { column | * } , ‘freetext_string’ [ , top_n_by_rank ] )
该函数使用与FREETEXT谓词相同的搜索条件。
(3) OPENDATASOURCE函数
该函数使用户连接到服务器。格式为:
OPENDATASOURCE (provider_name , init_string )
其中provider_name是注册为用于访问数据源的OLE DB 提供程序的 PROGID 的名称,init_string是连接字符串,这些字符串将要传递给目标提供程序的 IDataInitialize 接口。
例如:
SELECT *
FROMOPENDATASOURCE
( 'SQLOLEDB','Data Source=ServerName;UserID=MyUID;Password=MyPass'
).Northwind.dbo.Categories
4.1.3 FROM子句
(4) OPENQUERY函数
该函数在给定的链接服务器(一个 OLE DB 数据源)上执行指定的直接传递查询,返回查询的结果集。格式为:
OPENQUERY (linked_server , ‘query’ )
其中linked_server为连接的服务器名,query是查询命令串。
例如:
EXECsp_addlinkedserver 'OSvr', 'Oracle 7.3',
'MSDAORA',
'ORCLDB'
GO
SELECT *
FROMOPENQUERY(OSvr, 'SELECT title, id FROM al.book')
GO
该例使用为Oracle提供的OLE DB对Oracle数据库创建了一个名为Osvr的连接服务器,然后对该其进行检索。
(5) OPENROWSET函数
该函数与OPENQUERY函数功能相同。
(6) OPENXML函数
OPENXML 通过XML文档提供行集视图。
4.1.3 FROM子句
4. derived_table
derived_table是由SELECT查询语句的执行而返回的表,必须使用为其指定一个别名,也可以为列指定别名。
【例4.19】在XS表中查找1990年1月1日以前出生的学生的姓名和专业名,分别使用别名stu_name和speciality表示。
SELECTm.stu_name,m.speciality
FROM ( SELECT *FROM XS WHERE 出生时间<'19900101' ) AS m
(num,stu_name,speciality,sex,birthday,score,mem ,photo )
注意,若要为列指定别名,则必须为所有列指定别名。
执行结果如图4.11所示。
5. joined_table
joined_table为连接表,将在下一小节介绍。
4.1.4 连接
连接是两元运算,可以两个或多个表进行查询,结果通常是含有参加连接运算的两个表(或多个表)的指定列的表。例如在XSCJ数据库中需要查找选修了离散数学课程的学生的姓名和成绩,就需要将XS、KC和XS_KC三个表进行连接,才能查找到结果。
在T-SQL中,连接查询有两大类表示形式,一是符合SQL标准连接谓词表示形式,一是T-SQL扩展的使用关键字JOIN的表示形式。
1. 连接谓词
可以在SELECT语句的WHERE子句中使用比较运算符给出连接条件对表进行连接,将这种表示形式称为连接谓词表示形式。
【例4.20】查找XSCJ数据库每个学生的情况以及选修的课程情况。
SELECT XS.* ,XS_KC.*
FROM XS , XS_KC
WHERE XS.学号 = XS_KC.学号
4.1.4 连接
【例4.21】自然连接查询
SELECT XS.* ,XS_KC.课程号, XS_KC.成绩
FROM XS , XS_KC
WHERE XS.学号= XS_KC.学号
本例所得的结果表包含以下字段:学号、姓名、专业名、性别、出生时间、总学分、备注、课程号、成绩。
若选择的字段名在各个表中是唯一的,则可以省略字段名前的表名。如本例的 SELECT子句也可写为:
SELECT XS.* , 课程号, 成绩
FROM XS , XS_KC
WHERE XS.学号 = XS_KC.学号
【例4.22】查找选修了206课程且成绩在80分以上的学生姓名及成绩。
SELECT 姓名 , 成绩
FROM XS , XS_KC
WHERE XS.学号 = XS_KC.学号 AND 课程号 = ‘206’ AND 成绩 >= 80
4.1.4 连接
【例4.23】查找选修了“计算机基础”课程且成绩在80分以上的学生学号、姓名、课程名及成绩。
SELECT XS.学号, 姓名, 课程名, 成绩
FROM XS , KC ,XS_KC
WHERE XS.学号 = XS_KC.学号 AND KC.课程号 = XS_KC.课程号
AND 课程名 = ‘计算机基础’ AND 成绩 >= 80
4.1.4 连接
2. 以JOIN关键字指定的连接
对两个表之间的简单内部连接(不匹配的行将从结果中删除),通过在FROM字句中列出多个,并在WHERE子句中加上连接条件即可完成这个功能。而对更复诊的外部连接(不匹配的行需要保留),或者多一个一个连接的查询中用到的表多于两个,那么在FORM子句中需要明确的连接句法。T-SQL扩展了以JOIN关键字指定连接的表示方式,使表的连接运算能力有了增强。FROM子句的joined_table表示将多个表连接起来。
4.1.4 连接
::=
ON
| CROSS JOIN
|
其中table_source为指定要在Transact-SQL语句中使用的表或视图(带或不带别名均可),join_type表示连接类型,ON用于指定连接条件。join_type的格式为:
[ INNER | { LEFT |RIGHT | FULL } [ OUTER ] [ ] JOIN
其中INNER表示内连接,OUTER表示外连接,join_hint是连接提示。
CROSS JOIN表示交叉连接。因此,以JOIN关键字指定的连接有三种类型:
(1) 内连接
内连接按照ON所指定的连接条件合并两个表,返回满足条件的行。
【例4.24】查找XSCJ数据库每个学生的情况以及选修的课程情况。
SELECT *
FROM XS INNER JOINXS_KC
ON XS.学号 = XS_KC.学号
4.1.4 连接
结果表将包含XS表和XS_KC表的所有字段(不去除重复字段—学号)。若要去除重复的学号字段,可将SELECT子句改为:
SELECT XS.* , 课程号, 成绩
内连接是系统默认的,可以省略INNER关键字。使用内连接后仍可使用WHERE子句指定条件。
【例4.25】用FROM的JOIN关键字表达下列查询:查找选修了206课程且成绩在80分以上的学生姓名及成绩。
SELECT 姓名 , 成绩
FROM XS JOIN XS_KCON XS.学号 = XS_KC.学号
WHERE 课程号 = '206' AND成绩>=80
内连接还可以用于多个表的连接。
【例4.26】用FROM的JOIN关键字表达下列查询:查找选修了“计算机基础”课程且成绩在80分以上的学生学号、姓名、课程名及成绩。
SELECT XS.学号 , 姓名 , 课程名 , 成绩
FROM XS JOIN XS_KCJOIN KC ON XS_KC.课程号 = KC.课程号
ON XS.学号 = XS_KC.学号
WHERE 课程名 = '计算机基础' AND 成绩>=80
作为一种特例,可以将一个表与它自身进行连接,称为自连接。若要在一个表中查找具有相同列值的行,则可以使用自连接。使用自连接时需为表指定两个别名,且对所有列的引用均要用别名限定。
4.1.4 连接
【例4.27】查找不同课程成绩相同的学生的学号、课程号和成绩。
SELECT a.学号,a.课程号,b.课程号,a.成绩
FROM XS_KC a JOINXS_KC b
ON a.成绩=b.成绩 AND a.学号=b.学号 AND a.课程号!=b.课程号
图4.15查找不同课程成绩相同的学生的学号、课程号和成绩
(2) 外连接
外连接的结果表不但包含满足连接条件的行,还包括相应表中的所有行。外连接包括三种:
● 左外连接(LEFT OUTER JOIN):结果表中除了包括满足连接条件的行外,还包括左表的所有行;
● 右外连接(RIGHT OUTER JOIN):结果表中除了包括满足连接条件的行外,还包括右表的所有行;
4.1.4 连接
● 完全外连接(FULL OUTER JOIN):结果表中除了包括满足连接条件的行外,还包括两个表的所有行。
其中的OUTER关键字均可省略。
【例4.28】查找所有学生情况,及他们选修的课程号,若学生未选修任何课,也要包括其情况。
SELECT XS.* , 课程号
FROM XS LEFT OUTERJOIN XS_KC ON XS.学号 = XS_KC.学号
本例执行时,若有学生未选任何课程,则结果表中相应行的课程号字段值为NULL。
【例4.29】查找被选修了的课程的选修情况和所有开设的课程名。
SELECT XS_KC.* , 课程名
FROM XS_KC RIGHTJOIN KC ON XS_KC.课程号= KC.课程号
本例执行时,若某课程未被选修,则结果表中相应行的学号、课程号和成绩字段值均为NULL。
注意外连接只能对两个表进行。
(3) 交叉连接
交叉连接实际上是将两个表进行笛卡尔积运算,结果表是由第一个表的每行与第二个表的每一行拼接后形成的表,因此结果表的行数等于两个表行数之积。
【例4.30】列出学生所有可能的选课情况。
SELECT 学号,姓名,课程号,课程名
FROM XS CROSS JOINKC
注意: 交叉连接不能有条件,且不能带WHERE子句。
来自 “ ITPUB博客 ” ,链接:https://blog.itpub.net/345878/viewspace-1116193/ ,如需转载,请注明出处,否则将追究法律责任。