使用IN子句优化oracle查询

时间:2014-08-19 22:08:19

标签: java sql oracle query-optimization

我在参数中使用了两个查询,我使用PreparedStatementsetLong操作填充setString

查询1

SELECT A, B FROM TABLE1 WHERE A in  (SELECT A FROM TABLE2 WHERE C in (?,?,?) )

查询2

SELECT A, B FROM TABLE1 WHERE A in (?,?)

我被告知它会为每个可能的集合大小创建一个唯一的查询,并污染Oracle的SQL缓存。此外,oracle可以为每个查询选择不同的执行计划,因为大小不固定。

可以应用哪些优化来使其更好?

如果我创建大小为50的子句列表并使用虚拟/冗余变量填充剩余的列表,那会没关系吗?

如果我没有错,那么in-clause中的select-statement将难以优化,除非将其提取出来并再次用作语句列表。

1 个答案:

答案 0 :(得分:5)

  

我被告知它会为每个可能的设置大小创建一个唯一的查询,并污染Oracle的SQL缓存。

这是正确的,假设IN列表中的项目数可以在请求之间更改。如果IN列表中的问号数量保持不变,则不会对缓存造成“污染”。

  

此外,oracle可以为每个查询选择不同的执行计划,因为大小不固定。

这也是正确的。不过,这是一件好事。

  

可以应用哪些优化来使其更好?如果我创建大小为50的子句列表并使用虚拟/冗余变量填充剩余的列表,那会没关系吗?

绝对。我多次使用这个技巧:我生成了一个可以被一定数量整除的长度列表,而不是生成一个确切大小的列表(我使用了16,但50也很好)。如果实际列表的大小不能被16整除,我会将最后一项添加到达到正确长度所需的次数。

这实现的唯一优化是减少查询计划缓存中的项目。