视图按照其是否涉及DML操作,又可分为如下两类。
简单视图:视图的数据仅来自一个表,在视图的SELECT语句中不包含函数或数据分组,总是可以通过视图来执行DML操作。
复杂视图:视图的数据来自多个表,可以包含函数或数据分组,并不总是可以通过视图进行DML操作。
视图的创建语法如下所示。
- CREATE [OR REPLACE] [FORCE|NOFORCE] VIEW view
- [(alias[, alias]...)]
- AS subquery
- [WITH CHECK OPTION [CONSTRAINT constraint]]
- [WITH READ ONLY [CONSTRAINT constraint]];
语法中的关键字的含义如下所示。
OR REPLACE:如果视图已经存在,重新创建它。
FORCE:创建视图,而不管基表是否存在。
NOFORCE:只在基表存在的情况下创建视图(这是默认值)。
view:视图的名字。
alias:为由视图查询选择的表达式指定名字(别名的个数必须与由视图选择的表达式的个数匹配)。
subquery:是一个完整的SELECT 语句(对于在SELECT 列表中的字段,可以用别名)。
WITH CHECK OPTION:指定在视图中只有可访问的行才能被插入或修改。
constraint:为CHECK OPTION 约束指定的名字。
WITH READ ONLY:确保在该视图中没有DML操作被执行。
一般的创建视图的方式是先测试SELECT语句的正确性,然后将SELECT语句作为视图的subquery进行查询。
1.简单视图
简单视图是指基于单个表建立的,不包含任何函数、表达式和分组数据的视图。例如可以根据emp表中部门编号为20的员工创建一个视图,如以下语句所示。
上述语法是创建视图的最简单的语法形式,可以像使用表一样来使用这个视图,例如可以查看视图结果,对视图应用DML语句。下面的语句查询视图数据:
- SQL> CREATE OR REPLACE VIEW v_deptemp
- AS
- SELECT empno, ename, job, mgr, hiredate, sal, comm
- FROM emp
- WHERE deptno = 20;
- 视图已创建。
下面的语句向视图v_deptemp中插入了一条新的记录:
- SQL> SELECT * FROM v_deptemp;
- EMPNO ENAME JOB MGR HIREDATE SAL COMM
- ----- ----- ------------ ------ ------------ ----------- ----------
- 7369 史密斯 职员 7902 17-12月-80 2425.08 300
- 7566 约翰 经理 7839 02-4月 -81 3570 297.5
- 7788 斯科特 职员 7566 09-12月-82 1760.2 129.6
- 7876 亚当斯 职员 7788 12-1月 -83 1440 120
- 7902 福特 分析人员 7566 03-12月-81 3600 300
- 7892 张八 IT
- 7893 霍九
- 7894 霍十
- 已选择8行。
- SQL> INSERT INTO v_deptemp VALUES(7999,'李思','经理',7369,SYSDATE,8000,NULL);
- 已创建 1 行。
如果需要限制向视图插入数据,只插入满足视图中约束条件的数据,例如向v_deptemp视图中插入的数据要符合deptno为20这个约束,可以使用WITH CHECK OPTION选项定义CHECK约束。如果在视图上执行INSERT、UPDATE和DELETE语句,就要求所操作的数据必须是SELECT查询所能选择出来的数据,示例如代码5.15所示。
代码5.15 创建并操纵视图
- SQL> CREATE OR REPLACE VIEW v_deptemp_check
- AS
- SELECT empno, ename, job, mgr, hiredate, sal, comm, deptno
- FROM emp
- WHERE deptno = 20
- WITH CHECK OPTION CONSTRAINT v_empdept_chk;
- 视图已创建。
- SQL> INSERT INTO v_deptemp_check
- VALUES (7992, '赵六', '职员', 7369, SYSDATE, 8000, NULL, 30);
- INSERT INTO v_deptemp_check
- *
- 第 1 行出现错误:
- ORA-01402: 视图 WITH CHECK OPTION where 子句违规