2016-11-23 58 views
1
CREATE TABLE ak_temp 
(
    misc_1 varchar2(4000), 
    misc_2 varchar2(4000), 
    time_of_insert timestamp 
); 

查詢1(原件):關於Oracle查詢功能行爲

select * 
    from ak_temp 
where misc_1 in('ankush') 
    or misc_2 in('ankush') 

查詢2:

select * 
    from ak_temp 
where 'ankush' in (misc_1,misc_2) 

您好,我有幾分相似的問題與疑問,我希望避免查詢1,因爲我們的生活環境中的成本正在上升,因此我已經用較少的成本計算出了查詢2,它們在功能上是否相同?

回答

3

這兩者在功能上是等同的,應該產生相同的查詢計劃,所以不應該有比其他的性能優勢(或者任何這樣的優勢會很小)。 Oracle可能足夠聰明,可以利用兩個索引,一個索引ak_temp(misc_1),另一個索引ak_temp(misc_2)

但是,您也可以考慮:

select t.* 
from ak_temp t 
where misc_1 = 'ankush' 
union 
select t.* 
from ak_temp t 
where misc_2 = 'ankush'; 

這個版本肯定會採取指標的優勢,但如果多行符合兩個條件union可以慢下來。

編輯:

爲了避免union,你可以這樣做:

select t.* 
from ak_temp t 
where misc_1 = 'ankush' 
union all 
select t.* 
from ak_temp t 
where misc_2 = 'ankush' and (misc_1 <> 'ankush' and misc_1 is not null); -- or use `lnnvl()` 
+1

'Union'可避免,並且可以用repaced'UNION ALL'與[LNNVL(HTTPS的幫助: //docs.oracle.com/cd/B19306_01/server.102/b14200/functions078.htm)函數用於查詢的底部分支 - 也就是'where misc_2 ='ankush'AND LNNVL(misc_1 ='ankush') '。有關更多詳細信息,請參閱此鏈接:[Oracle - OR擴展](https://blogs.oracle.com/optimizer/entry/或擴展轉換)。順便說一句''union'只能在假設表不包含重複行的情況下工作,否則它不等同於oryginal查詢,它會給出錯誤的結果。 – krokodilko