我相信 Oracle 优化器 足够聪明,可以转换查询 并在这两种情况下使用最佳执行计划。因此,很有可能根本没有任何区别。
为什么不测试一下看看。
基表上没有索引
案例#1现有观点
SQL> CREATE OR REPLACE VIEW emp_view AS SELECT empno, ename, deptno, JOB, sal, mgr FROM emp;
View created.
SQL>
SQL> EXPLAIN PLAN FOR
2 SELECT * FROM emp
3 where empno = (select empno from emp_view where ename='SCOTT');
Explained.
SQL>
SQL> SELECT * FROM TABLE(dbms_xplan.display);
PLAN_TABLE_OUTPUT
--------------------------------------------------------------------------------
Plan hash value: 587534197
---------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
---------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 37 | 6 (0)| 00:00:01 |
|* 1 | TABLE ACCESS FULL | EMP | 1 | 37 | 3 (0)| 00:00:01 |
|* 2 | TABLE ACCESS FULL| EMP | 1 | 10 | 3 (0)| 00:00:01 |
---------------------------------------------------------------------------
Predicate Information (identified by operation id):
PLAN_TABLE_OUTPUT
--------------------------------------------------------------------------------
---------------------------------------------------
1 - filter("EMPNO"= (SELECT "EMPNO" FROM LALIT."EMP" "EMP" WHERE
"ENAME"='SCOTT'))
2 - filter("ENAME"='SCOTT')
16 rows selected.
SQL>
案例#2自定义视图
SQL> CREATE OR REPLACE VIEW emp_custom_view AS SELECT empno, ename FROM emp;
View created.
SQL>
SQL> EXPLAIN PLAN FOR
2 SELECT * FROM emp
3 WHERE empno = (SELECT empno FROM emp_custom_view WHERE ename='SCOTT');
Explained.
SQL>
SQL> SELECT * FROM TABLE(dbms_xplan.display);
PLAN_TABLE_OUTPUT
--------------------------------------------------------------------------------
Plan hash value: 587534197
---------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
---------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 37 | 6 (0)| 00:00:01 |
|* 1 | TABLE ACCESS FULL | EMP | 1 | 37 | 3 (0)| 00:00:01 |
|* 2 | TABLE ACCESS FULL| EMP | 1 | 10 | 3 (0)| 00:00:01 |
---------------------------------------------------------------------------
Predicate Information (identified by operation id):
PLAN_TABLE_OUTPUT
--------------------------------------------------------------------------------
---------------------------------------------------
1 - filter("EMPNO"= (SELECT "EMPNO" FROM LALIT."EMP" "EMP" WHERE
"ENAME"='SCOTT'))
2 - filter("ENAME"='SCOTT')
16 rows selected.
SQL>
在基表上使用索引,并在过滤谓词中使用索引列
案例#1 现有视图
SQL> CREATE OR REPLACE VIEW emp_view AS SELECT empno, ename, deptno, JOB, sal, mgr FROM emp;
View created.
SQL>
SQL> EXPLAIN PLAN FOR
2 SELECT * FROM emp
3 where empno = (select empno from emp_view where empno= 7369);
Explained.
SQL>
SQL> SELECT * FROM TABLE(dbms_xplan.display);
PLAN_TABLE_OUTPUT
--------------------------------------------------------------------------------------------
Plan hash value: 4162864836
--------------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
--------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 39 | 1 (0)| 00:00:01 |
| 1 | TABLE ACCESS BY INDEX ROWID| EMP | 1 | 39 | 1 (0)| 00:00:01 |
|* 2 | INDEX UNIQUE SCAN | PK_EMP | 1 | | 0 (0)| 00:00:01 |
|* 3 | INDEX UNIQUE SCAN | PK_EMP | 1 | 4 | 0 (0)| 00:00:01 |
--------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
2 - access("EMPNO"= (SELECT "EMPNO" FROM SCOTT."EMP" "EMP" WHERE
"EMPNO"=7369))
3 - access("EMPNO"=7369)
17 rows selected.
SQL>
案例#2 自定义视图
SQL> CREATE OR REPLACE VIEW emp_custom_view AS SELECT empno, ename FROM emp;
View created.
SQL>
SQL> EXPLAIN PLAN FOR
2 SELECT * FROM emp
3 WHERE empno = (SELECT empno FROM emp_custom_view WHERE empno=7369);
Explained.
SQL>
SQL> SELECT * FROM TABLE(dbms_xplan.display);
PLAN_TABLE_OUTPUT
----------------------------------------------------------------------------------------------
Plan hash value: 4162864836
--------------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
--------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 39 | 1 (0)| 00:00:01 |
| 1 | TABLE ACCESS BY INDEX ROWID| EMP | 1 | 39 | 1 (0)| 00:00:01 |
|* 2 | INDEX UNIQUE SCAN | PK_EMP | 1 | | 0 (0)| 00:00:01 |
|* 3 | INDEX UNIQUE SCAN | PK_EMP | 1 | 4 | 0 (0)| 00:00:01 |
--------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
2 - access("EMPNO"= (SELECT "EMPNO" FROM SCOTT."EMP" "EMP" WHERE
"EMPNO"=7369))
3 - access("EMPNO"=7369)
17 rows selected.
SQL>
所以,这两种情况下的解释计划是完全一样的。