日期:2014-05-16 浏览次数:20582 次
Operator Returns
UNION(联合) 由每个查询选择的所有不同的行(无重复值)
UNION ALL 由每个查询选择的所有的行,包括所有重复的行
INTERSECT(交叉) 由两个查询选择的所有不同的行
MINUS 由第一个查询选择的所有不同的行
所有的集合运算与等号的优先级相同,如果SQL语句包含多个集合运算并且没有圆括号明确地指定另一个顺序,Oracle服务器将以从左到右的顺序计算。你应该使用圆括号来明确地指定带另外的集合运算的INTERSECT (相交) 运算查询中的赋值顺序。
注:在幻灯片中,图中的亮色代表查询结果。
INTERSECT (相交) 和MINUS (相减) 运算不是ANSI SQL-99兼容的,他们是Oracle特定的。
在下面要用到的表:
:: EMPLOYEES: 提供所有在职雇员当前的详细资料
:: JOB_HISTORY:当一个雇员改变工作时,记录他的以前的工作的开始日期和结束日期、
departmentID和job ID的详细资料
SQL> desc employees;
名称 是否为空? 类型
----------------------------------------- -------- -------------
EMPLOYEE_ID NOT NULL NUMBER(6)
FIRST_NAME VARCHAR2(20)
LAST_NAME NOT NULL VARCHAR2(25)
EMAIL NOT NULL VARCHAR2(25)
PHONE_NUMBER VARCHAR2(20)
HIRE_DATE NOT NULL DATE
JOB_ID NOT NULL VARCHAR2(10)
SALARY NUMBER(8,2)
COMMISSION_PCT NUMBER(2,2)
MANAGER_ID NUMBER(6)
DEPARTMENT_ID NUMBER(4)
QL> desc job_history
名称 是否为空? 类型
---------------------- -------- -------------
EMPLOYEE_ID NOT NULL NUMBER(6)
START_DATE NOT NULL DATE
END_DATE NOT NULL DATE
JOB_ID NOT NULL VARCHAR2(10)
DEPARTMENT_ID NUMBER(4)
[b]联合运算[/b]
联合(UNION) 运算从两个查询返回除去重复值后的结果
UNION(联合)运算
UNION运算返回所有由任一查询选择的行。用UNION运算从多表返回所有行,但除去任何重复的行。
原则./././././
:: 被选择的列数和列的数据类型必须是与所有用在查询中的SELECT语句一致。列的名字不必相同。
:: 联合运算在所有被选择的列上进行。
:: 在做重复检查的时候不忽略空(NULL)值。././././
:: IN运算有比UNION运算高的优先级。
:: 在默认情况下,输出以SELECT子句的第一列的升序排序。./././././
[b]使用联合集合运算[/b]
显示当前和以前所有雇员的工作岗位。每个雇员仅显示一次
SELECT employee_id, job_id
FROM employees
UNION
SELECT employee_id, job_id
FROM job_history;
使用联合集合(UNION SET)运算
联合运算消除重复记录,如果有相同的记录同时出现在EMPLOYEES和JOB_HISTORY表中,该记录只显示一次,观察幻灯片的输出显示雇员号为200的雇员的雇员号虽然显示了两次,但每一行的JOB_ID是不同的。
考虑下面的例子:
SELECT employee_id, job_id, department_id
FROM employees
UNION
SELECT employee_id, job_id, department_id
FROM job_history;
EMPLOYEE_ID JOB_ID DEPARTMENT_ID
100
200 AC_ACCOUNT 90
200 AD_ASST 10
200 AD_ASST 90
...
600
使用联合集合(UNION SET)运算 (续)
在前面的输出中,雇员200出现了3次,为什么?注意雇员200的DEPARTMENT_ID值,一行是90,另一行是10,第三行是90,因为这些job_id和department_id的唯一组合,对于每行的雇员200是唯一的,因此他们是不重复的。
观察输出以SELECT子句的第一列的升序排序,即以EMPLOYEE_ID排序。
[b]全联合运算[/b]
全联合(UNION ALL) 运算从两个查询返回包括所有重复值的结果
全联合(UNION ALL)运算
用全联合运算从多个查询中返回所有行。
原则 ./././././././././
:: 和联合不同,重复的行不被过滤,并且默认情况下输出不排序。
:: 不能使用DISTINCT关键字。
注:除了上面的两点,UNION ALL的原则与UNION相同。
[b]使用全联合运算[/b]
显示当前和以前所有雇员所在的部门
SELECT employee_id, job_id, department_id
FROM employees
UNION ALL
SELECT employee_id, job_id, department_id
FROM job_history
ORDER BY employee_id;
EMPLOYEE_ID JOB_ID DEPARTMENT_ID
100
200 AD_ASST 10
200 AD_ASST 90
200 AC_ACCOUNT 90
...
600
[b]
全联合(UNION ALL)运算 (续)[/b]
在例子中,有30行被选择,两个表组合到共30行中,全联合运算不会消除重复的行,在幻灯片中重复的行被突出显示,联合返回任一查询所选择的所有不重复的行,而全联合返回任一查询所选择的所有行,包括所有重复。
现在用联合子句来写:
SELECT employee_id, job_id,department_id
FROM employees
UNION
SELECT employee_id, job_id,department_id
FROM job_history
ORDER BY employee_id;
上面的查询返回29行,这是因为下面的行被除去了(因为它是一个重复行):
176 SA_REP 80
[b]
相交运算
[/b]
相交(INTERSECT) 运算返回多个查询中所有相同的行
相交运算
用相交运算返回多个查询中所有的公共行。
原则 ./././.列数和数据类型
:: 在查询中被 SELECT 语句选择的列数和数据类型必须与在查询中所使用的所有的 SELTCT 语句中的 一样,但列的名字不必一样。
:: 颠倒相交的表的排序不改变结果。
:: 相交不忽略空值。
[b]使用相交运算[/b]
显示雇员表的employee_ID 和job_ID,这些雇员当前所做的工作是以前他们做过一端时间,后来有变化,现在又在做的工作。
SQL> SELECT employee_id, job_id
2 FROM employees
3 INTERSECT
4 SELECT employee_id, job_id
5 FR