星期日, 七月 16, 2006

[翻译]SQL中的连接

第四章 连接

感觉像个老手了?让我马上把你这种感觉击碎吧(开个玩笑)!尽管我们已经学习了基本的语句,但是他们只是我们将要学习的语句的一小部分。简单说来,你只使用一张表是干不了什么事情的,特别是在一个高度规格化的数据库中。

一个规格化的数据库就是为了防止数据重复,节省存储空间,提高运算性能和提高数据的完整性,而讲大一点的表格划分成许多小一点的表格的数据库。它对于关系数据库是重要且必不可少的,但这同样以为着你将对付这里,那里的各种数据。

我们将在第八章扩展了解规格化的概念。现在,我们只是记住数据库越规整,你将越有可能不得不将许多表格连接起来,以得到你想要的数据。

在本单元,我们将给你介绍通过使用各种JOIN语句,把许多表格结合成一个结果集(Result Set)的过程。他们包括
❑ INNER JOIN
❑ OUTER JOIN (both LEFT and RIGHT)
❑ FULL JOIN
❑ CROSS JOIN

我们同样将学习不止一种语句结构来实现连接,只有一种特别的语句结构才是正确的选择。此外,我们将学习UNION操作符,它可以用来将两个搜索的结果结合成一个。

连接
当我们在一个规格化的环境里进行操作时,我们经常遇到这样的情况,就是我们需要的信息不是只来源于同一个表格。在其他的情况下,我们需要的所有信息是来源于一个表格,但我们需要设置的一些条件则来源于另外一个表格。在这种情况下,正是JOIN语句大显身手的地方。

一个JOIN并不是看起来那么简单——把两个表格的各种信息放到一个结果集里。我们可以把结果集看成是一个“虚拟”表格。它也有排和列,列有数据类型。实际上,在第七章,大家将看到如何象一个表格一样对待结果集,并且用它来进行其他查询。

究竟一个JOIN 操作是如何将两个表里面的信息放到一个结果集的?噢,这个取决于你是如何描述把这些数据放在一起的方式的——这就是为何这里有四种JOIN的原因。所有JOIN操作的共同点就是将一个同另外一个或一个以上的记录相配,然后形成两个记录相结合的超集。

例如,我们以一个叫做表格Film的记录为例

FilmID
FilmName
YearMade
1
My Fair Lady
1964


接着是叫做表格Actor的记录:

FilmID
FirstName
LastName
1
Rex
Harrison

使用JOIN操作,我们可以将两个完全分开的表格的记录创建到一个记录中。
FilmID
FilmName
YearMade
FirstName
LastName
1
My Fair Lady
1964
Rex
Harrison

这个JOIN操作(至少在表面上)用一对一的关系将记录连接起来。我们用一个Film记录连接了一个Actors记录。

让我们把问题拓展一点,来看看你是否能够理解现在发生的一切。我已在Actor表格中加入了另外一条记录:

FilmID
FirstName
LastName
1
Rex
Harrison
1
Audrey
Hepburn

让我们来看看我们连接这个非常相似的Film表格后的结果:
FilmID
FilmName
YearMade
FirstName
LastName
1
My Fair Lady
1964
Rex
Harrison
1
My Fair Lady
1964
Audrey
Hepburn

正如你可以看见的,结果改变了一点-我们不再把事情看作是一对一的,而是一对二,或者更确切的说是一对多关系。我们可以使用在Film表格中无限多次使用单独一条记录来完成关于匹配的Actor表格中信息。你主要到他们怎么匹配的吗?当然,他们通过匹配两个表格的FilmID来形成共同的记录。我们使用的例子,它只有很有限的记录,但可以真实地形成同样地结果,无论我们使用的是什么JOIN类型。现在就让哦我们来看看不同JOIN了行的特点吧。

内联(INNER JOINs)

内联(INNER JOINs)与一般的连接很不一样。很多连接都是基于一个或多个基本区域来匹配记录,但是内联只返回你将用来连接的任何列的记录。在我们先前的例子中,每个记录至少会在结果集中出现一次,但是这样的情况在现实生活中非常稀少。让我们修改一下我们的表格,来看看我们将从内联中得到什么。这是我们的Film表格:

FilmID
FilmName
YearMade
1
My Fair Lady
1964
2
Unforgiven
1992


还有Actor表格:

FilmID
FirstName
LastName
1
Rex
Harrison
1
Audrey
Hepburn
2
Clint
Eastwood
5
Humphrey
Bogart

使用内联,我们的结果集将会是:

FilmID
FirstName
LastName
1
Rex
Harrison
1
Audrey
Hepburn
2
Clint
Eastwood

请注意Bogart已经被排除在结果集之外。这是因为它在Film表格中没有匹配的记录。如果在两国表格中都没有匹配的记录,那么查询的记录也不会返回。好了,理论够多的了,让我们试试这些代码。

内联(INNER JOIN)的首选代码应该是这个样子:
SELECT

没有评论: