3.3 SQL查询的基本结构 3.3.1 单关系查询

3.3 SQL查询的基本结构

SQL查询的基本结构由三个子句构成:selectfromwhere
查询的输入是在from子句中列出的关系,在这些关系上进行whereselect子句中指定的运算,然后产生一个关系作为结果。
我们通过例子介绍SQL的语法,后面再描述SQL查询的通用结构。

3.3.1 单关系查询

instructor关系模式定义如下

instructor(ID,name,dept_name,salary)

找出所有教师的名字

我们考虑使用大学数据库例子的一个简单查询:**”找出所有教师的名字”**。教师的名字可以在instructor关系中找到,因此我们把instructor关系放到from子句中。教师的名字出现在name属性中,因此我们把name放到select子句中。

1
select name from instructor;

其结果是由属性名为name的单个属性构成的关系。

找出所有教师所在的系名

现在考虑另一个查询:”找出所有教师所在的系名”,此查询可写为:

1
select dept_name from instructor;

因为一个系有多个教师,所以在instructor关系中,一个系的名称可以出现不止一次。
在关系模型的形式化数学定义中,关系是一个集合。因此,重复的元组不会出现在关系中。
在实践中,去除重复是相当费时的,所以**SQL允许在关系以及SQL表达式结果中出现重复**。因此,在上述SQL查询中,每个系名在instructor关系的元组中每出现一次,都会在查询结果中列出一次。

去除查询结果中的重复 select distinct

有时候我们想要强行删除重复,可select后加入distinct关键词。如果我们想去除重复,可将上述查询重写为:

1
select distinct dept_name from instructor;

在上述查询的结果中,每个系名最多只出现一次。

保留查询结果中的重复 select all

SQL允许我们使用关键词all来显式指明不去除重复:

1
select all dept_name from instructor;

不过SQL是默认保留重复元组的,所以all关键词可以省略。

算术运算符

select子句还可带含有加(+)、减(-)、乘(*)、除(/)运算符的算术表达式。

算术运算符可用于常数或者元组的属性

算术运算符的运算对象可以是常数或元组的属性。例如,查询语句:

1
select ID, name, dept_name, salary*1.1 from instructor;

将返回一个与instructor一样的关系,只是属性salary的值是原来的1.1倍。这显示了如果我们给每位教师增长10%的工资的结果。注意这并不导致对instructor关系的任何改变。

特定类型的算术函数

SQL还提供了一些特殊数据类型,如各种形式的日期类型,并允许一些作用于这些类型上的算术函数。我们在4.5.1节进一步讨论这个问题。

where子句

where子句允许我们只选出那些在from子句的结果关系中满足特定谓词的元组。

找出所有在Computer Science系并且工资超过70000美元的教师的姓名

考虑查询”找出所有在Computer Science系并且工资超过70000美元的教师的姓名”,该查询用SQL可以写为:

1
2
select name from instructor
where dept_name ='Comp.Sci' and salary >70000;

逻辑连词

SQL允许在where子句中使用逻辑连词andornot

逻辑连词的运算对象是包含比较运算符的表达式

**逻辑连词运算对象**可以是**包含比较运算符**<<=>>==<>**的表达式**。 SQL允许我们使用比较运算符来比较字符串、算术表达式以及特殊类型,如日期类型。 在本章的后面,我们将研究where`子句谓词的其他特征。

大学数据库模式

classroom(building,room_number,capacity)
department(dept_name,building,budget)
course(course_id,title,dept_name,credits)
instructor(ID,name,dept_name,salary)
section(course_id,sec_id,semester,year,building,room_number,time_slot_id)
teaches(ID,course_id,sec_id,semester,year)
student(ID,name,dept_name,tot_cred)
takes(ID,course_id,sec_id,semester,year,grade)
advisor(s_ID,i_ID)
time_slot(time_slot_id,day,start_time,end_time)
prereq(course_id,prereq_id)