子查询是否保留索引

时间:2013-06-11 08:44:53

标签: sql oracle

我想知道Oracle中子查询返回的值是否会丢失索引。

select * from emp where empid = 1
-- empid is indexed
select t1.* from (select t2.* from emp t2) t1 where t1.empid = 1  
-- t1.empid  is still indexed?

3 个答案:

答案 0 :(得分:3)

是的,第二个查询使用索引。实际上,两者都编译成完全相同的执行计划。在SQLFiddle上查看。

您应该记住SQL处理是惰性的:子查询不一定完全执行以将输入数据提供给顶级查询。相反,它们应被视为可根据需要调用以获取该数据的代码。

答案 1 :(得分:1)

查询优化过程的一部分是简化提供的查询的结构。这通常意味着用连接替换IN和EXISTS,将谓词推入内联视图并完全消除子查询。

事实上,因为这种行为如此普遍,所以有一些技术(例如,优化器提示,或公共表表达式,或某些逻辑冗余子句)专门用于防止谓词推送和子查询合并以及其他查询转换。无意中不利。

默认情况下,您应该期望子视图和内联视图在逻辑上可以合并到父查询中,而且正如其他人所提到的那样,在您的示例中几乎可以肯定。

当然,从所有这些开始,使用子查询或内联视图通常不会影响优化器使用索引或查询重写或各种其他性能增强技术的能力。

答案 2 :(得分:0)

这个问题没有简单的答案:有时是,有时没有。这取决于很多因素。一般来说,只是不深入理论,尽量避免这种查询式写作方式安全,换句话说,大多数情况下视图都不好。有关详细信息,请参阅http://www.orafaq.com/tuningguide/push%20predicates.html