簡述
表結構
表 A -
A_SEQ_ID,
LVL1_NODE_ID,
LVL2_NODE_ID,
LVL3_NODE_ID,
LVL4_NODE_ID,
LVL5_NODE_ID,
LVL6_NODE_ID,
LVL7_NODE_ID,
LVL8_NODE_ID,
LVL9_NODE_ID,
LVL10_NODE_ID
表 B -
B_SEQ_ID,
NODE_ID,
INFO
開始時的 sql
SELECT * FROM A, B WHERE A.LVL1_NODE_ID = B.NODE_ID OR A.LVL2_NODE_ID = B.NODE_ID OR A.LVL3_NODE_ID = B.NODE_ID OR A.LVL4_NODE_ID = B.NODE_ID OR A.LVL5_NODE_ID = B.NODE_ID OR A.LVL6_NODE_ID = B.NODE_ID OR A.LVL7_NODE_ID = B.NODE_ID OR A.LVL8_NODE_ID = B.NODE_ID OR A.LVL9_NODE_ID = B.NODE_ID OR A.LVL10_NODE_ID = B.NODE_ID;
這條 sql雖然可以達到最終的目的,但是由於表 A和表 B的數據量比較大,所以執行起來相當慢。
使用 Instr函數
SELECT * FROM A, B WHERE instr( (','||A.LVL1_NODE_ID||','||A.LVL2_NODE_ID||','||A.LVL3_NODE_ID|| ','||A.LVL4_NODE_ID||','||A.LVL5_NODE_ID||','||A.LVL6_NODE_ID|| ','||A.LVL7_NODE_ID||','||A.LVL8_NODE_ID||','||A.LVL9_NODE_ID|| ','||A.LVL10_NODE_ID), ','||B.NODE_ID||',') > 0;
比起 OR語句一個字段一個字段的比較,instr函數更加高效。當 instr函數匹配到子串的時候就會返回子串在源字符串中的位置,所以這里用 大於0 即表示在表 A的源字符串中可以找到表 B的 NODE_ID (子串或源字符串為 NULL時返回 NULL)。
注:給每個字段加上逗號(',')的原因是匹配的一種方法,例如源數據是 1,2,3,13. 子串是 23.如果直接拼接的話,源字符串就變成 '12313',用instr('12313', '23') 明顯可以匹配成功,但事實並非如此。所以換成給每個字符兩邊都加上逗號,不僅匹配字符也匹配其兩邊的逗號 - instr(',1,2,3,13,', '23')。
Oracle Instr 函數

其中:
INSTR 接受 characters格式的輸入字符集,返回 characters格式的子串位置,位置索引從 1開始;
INSTRB 使用 bytes 而非 characters;
INSTRC 使用 Unicode complete characters;
INSTR2 使用UCS2 code points;
INSTR4 使用UCS4 code points。
對於源字符串,除了INSTRC, INSTR2, 和 INSTR4 不允許CLOB 和 NCLOB 類型外,其他兩個函數的源字符串接受CHAR, VARCHAR2, NCHAR, NVARCHAR2, CLOB 或 NCLOB等任意數據類型。
instr 語法如下: instr( string1, string2, start_position,nth_appearance )
string1
|
源字符串,要在此字符串中查找。
|
string2
|
要在string1中查找的字符串 。
|
start_position
|
代表string1 的哪個位置開始查找。此參數可選,如果省略默認為1. 字符串索引從1開始。如果此參數為正,從左到右開始檢索,如果此參數為負,從右到左檢索,返回要查找的字符串在源字符串中的開始索引。
|
nth_appearance
|
代表要查找第幾次出現的string2. 此參數可選,如果省略,默認為 1.如果為負數系統會報錯。
|
注意:
如果String2在String1中沒有找到,instr函數返回0。
示例:
SELECT instr('syranmo','s') FROM dual; -- 返回 1
SELECT instr('syranmo','ra') FROM dual; -- 返回 3
SELECT instr('syran mo','a',1,2) FROM dual; -- 返回 0