第4章SQL查询 查询是数据库的基本应用之一。Oracle中的SQL查询语 法,一方面遵循了SQL标准,另一方面又有自己的独特之处。 这些独特之处也使得Oracle中的SQL查询功能更加强大。本章 将详细讲述Oralce中的SQL查询语句,其主要内容包括。 基本查询:主要讲述查询语句及各种子句的使用 子查询:主要讲述如何在查询语句中添加子查询 联合语句:主要讲述多个查询语句之间的集合运算 关联语句:主要讲述多个表/视图之间的关联关系 层次化查询:主要讲述树状结构的查询 通过本章的学习,读者可以对FOracle中的查询语句有清 晰的了解,并对掌握Oracle本身的特色查询
Oracle SQL SQL Oracle SQL Oralce SQL / Oracle Oracle
4.1基本查询 一条查询语句有可能非常复杂,但都是由最简单的基 本查询组成。本节将重,点讲述Oracle中的基本查询语句
Oracle
4.1.1查询命令select 执行查询的命令为select命令,该命令用于在数据源中 捕获最终数据。无论查询语句多么复杂,最外层的select命 令总是最后执行。 【示例4-1】一个简单的查询员工表employees中所有员 工姓名的select语句如下所示。 select employee_name from employees; Oracle首先根据from子句获得数据源的所有记录,如 下所示。 EMPLOYEE ID EMPLOYEE NAME EMPLOYEE POSITION EMPLOYEE AGE EMPLOYEE ADDRESS
select select 4-1 employees select select employee_name from employees; Oracle from EMPLOYEE_ID EMPLOYEE_NAME EMPLOYEE_POSITION EMPLOYEE_AGE EMPLOYEE_ADDRESS
4.1.2指定过滤条件—where子句 where子句用于限定from子句所指定的数据源或者各数 据源进行运算之后形成的结果集合。因此,执行顺序处于 from子句之后,select命令之前。 【示例4-2】针对表employees,现欲获得年龄大于25岁 的所有员工姓名,则可以利用如下$QL语句。 select employee_name from employees where employee_age>25 该$QL语句的执行过程如下。 (1)根据from子句获得数据源,将获得表employees 中所有记录,如下所示。 EMPLOYEE ID EMPLOYEE NAME EMPLOYEE POSITION EMPLOYEE AGE EMPLOYEE ADDRESS
—— where from from select 4-2 employees 25 SQL select employee_name from employees where employee_age>25 SQL 1 from employees EMPLOYEE_ID EMPLOYEE_NAME EMPLOYEE_POSITION EMPLOYEE_AGE EMPLOYEE_ADDRESS
4.1.3获取唯一记录一distinct 在示例4-3中,我们会发现重复记录。这表明,员工领 取的工资在大多数月份中可能都是相同的。为了剔除其中的 重复记录,更清晰的展现员工工资状况,可以利用distinct 关键字。 【示例4-4】获取员工唯一工资状况的SQL语句如下所 示。 SQL>select distinct e.employee_name,s.salary 2 from employees e,salary s 3 where e.employee_id s.employee_id;
—— 4-3 distinct 4-4 SQL SQL> select distinct e.employee_name, s.salary 2 from employees e, salary s 3 where e.employee_id = s.employee_id;
4.1.4分组一group by子句 在数据库查询中,分组是一个非常重要的应用。分组 是指将数据表中所有记录中,以某个或者某些列为标准,划 分为一组。例如,在一个存储了地区学生的表中,以学校为 标准,可以将所有学生信息划分为多个组。 进行分组查询应该使用group by-子句。group by-子句指 定分组标准,并将数据源按照该标准进行划分,然后循环处 理每组数据
—— group by group by
4.1.5过滤分组—having子句 where-子句可以过滤from子句所指定的数据源,但是对 于group by子句所产生的分组无效。为了将分组按照一定条 件进行过滤,应该使用having子句。 【示例4-6】having子句是依附于group by-子句存在而 存在。在示例4-5中,为了获得工资总额大于10000的记录, 应该使用如下SQL语句。 select e.employee_id,e.employee_name,sum(s.salary) total salary from employees e,salary s where e.employee_id s.employee_id group by e.employee_id,e.employee_name having (sum(s.salary))>10000
—— where from group by having 4-6 having group by 4-5 10000 SQL select e.employee_id, e.employee_name, sum(s.salary) total_salary from employees e, salary s where e.employee_id = s.employee_id group by e.employee_id, e.employee_name having (sum(s.salary))>10000
4.1.6排序一order by子句 order by-子句用于排序结果集。order by-子句在使用时 需要指定排序标准和排序方式。排序标准是指按照结果集中 哪个或哪些列进行排序;order by.有两种排序方式一升序 (asc,同时也是默认排序方式)和降序(desc)。 【示例4-7】在示例4-4的查询结果中可以看到,没有指 定排序规则的情况下,搜寻结果是杂乱无章的。可以对该搜 寻结果按照工资水平由高到低的顺序排列,SQL语句如下所 示。 SQL>select distinct e.employee_name,s.salary 2 from employees e,salary s 3 where e.employee_id =s.employee_id 4 order by s.salary desc;
—— order by order by order by —— (asc ) desc 4-7 4-4 SQL SQL> select distinct e.employee_name, s.salary 2 from employees e, salary s 3 where e.employee_id = s.employee_id 4 order by s.salary desc;
4.1.7 order by与group by子句 本小节,我们来讨论一条SQL查询语句中同时存在order by与group by子句时的执行情况。当两种子句同时存在时, Oracle首先执行group by-子句,然后才进行排序操作。 【示例4-8】通过员工表employees-与工资表salary,我们 可以获得员工工资总额状况,并按照工资总额由高到低的顺 序进行排列。 SQL>select e.employee name,sum(s.salary)total_salary 2 from employees e,salary s 3 where e.employee_id s.employee_id 4 group by e.employee_name 5 order by total salary desc;
SQL order by group by Oracle group by 4-8 employees salary SQL> select e.employee_name, sum(s.salary) total_salary 2 from employees e, salary s 3 where e.employee_id = s.employee_id 4 group by e.employee_name 5 order by total_salary desc;
4.1.8 order bydistinct order by子句与distinct关键字同时使用时,也必须遵循 这样一个规则一order by子句所指定的排序列,必须出现 在select表达式中。 【示例4-9】我们可以通过表employees-与表salary获得 员工的单月工资状况。现欲获得所有员工姓名,并按工资进 行升序排列。 SQL>select e.employee_name 2 from employees e,salary s 3 where e.employee_id s.employee_id 4 order by s.salary 5/
order by distinct ——order by select 4-9 employees salary SQL> select e.employee_name 2 from employees e, salary s 3 where e.employee_id = s.employee_id 4 order by s.salary 5 /